Ignore:
Timestamp:
Dec 3, 2014, 3:08:38 PM (9 years ago)
Author:
Peter A. Buhr <pabuhr@…>
Branches:
ADT, aaron-thesis, arm-eh, ast-experimental, cleanup-dtors, ctor, deferred_resn, demangler, enum, forall-pointer-decay, gc_noraii, jacob/cs343-translation, jenkins-sandbox, master, memory, new-ast, new-ast-unique-expr, new-env, no_list, persistent-indexer, pthread-emulation, qualifiedEnum, resolv-new, string, with_gc
Children:
d9a0e76
Parents:
42dcae7
Message:

underscore changes, ptrdiff_t changes, formating, _Bool prelude

File:
1 edited

Legend:

Unmodified
Added
Removed
  • translator/Parser/DeclarationNode.cc

    r42dcae7 r3848e0e  
    2828extern LinkageSpec::Type linkage;               /* defined in cfa.y */
    2929
    30 DeclarationNode*
    31 DeclarationNode::clone() const
    32 {
    33   DeclarationNode *newnode = new DeclarationNode;
    34   newnode->type = maybeClone( type );
    35   newnode->name = name;
    36   newnode->storageClasses = storageClasses;
    37   newnode->bitfieldWidth = maybeClone( bitfieldWidth );
    38   newnode->hasEllipsis = hasEllipsis;
    39   newnode->initializer = initializer;
    40   newnode->next = maybeClone( next );
    41   newnode->linkage = linkage;
    42   return newnode;
    43 }
    44 
    45 DeclarationNode::DeclarationNode()
    46   : type( 0 ), bitfieldWidth( 0 ), initializer( 0 ), hasEllipsis( false ), linkage( ::linkage )
    47 {
    48 }
    49 
    50 DeclarationNode::~DeclarationNode()
    51 {
    52   delete type;
    53   delete bitfieldWidth;
    54   delete initializer;
    55 }
    56 
    57 bool
    58 DeclarationNode::get_hasEllipsis() const
    59 {
    60   return hasEllipsis;
    61 }
    62 
    63 const char *storageClassName[] =
    64 {
    65   // order must correspond with DeclarationNode::StorageClass
    66   "static",
    67   "auto",
    68   "extern",
    69   "register",
    70   "inline",
    71   "fortran",
     30DeclarationNode *DeclarationNode::clone() const {
     31    DeclarationNode *newnode = new DeclarationNode;
     32    newnode->type = maybeClone( type );
     33    newnode->name = name;
     34    newnode->storageClasses = storageClasses;
     35    newnode->bitfieldWidth = maybeClone( bitfieldWidth );
     36    newnode->hasEllipsis = hasEllipsis;
     37    newnode->initializer = initializer;
     38    newnode->next = maybeClone( next );
     39    newnode->linkage = linkage;
     40    return newnode;
     41}
     42
     43DeclarationNode::DeclarationNode() : type( 0 ), bitfieldWidth( 0 ), initializer( 0 ), hasEllipsis( false ), linkage( ::linkage ) {
     44}
     45
     46DeclarationNode::~DeclarationNode() {
     47    delete type;
     48    delete bitfieldWidth;
     49    delete initializer;
     50}
     51
     52bool DeclarationNode::get_hasEllipsis() const {
     53    return hasEllipsis;
     54}
     55
     56const char *storageClassName[] = {
     57    // order must correspond with DeclarationNode::StorageClass
     58    "static",
     59    "auto",
     60    "extern",
     61    "register",
     62    "inline",
     63    "fortran",
    7264};
    7365
    74 void
    75 DeclarationNode::print( std::ostream &os, int indent ) const
    76 {
    77   os << string(indent,  ' ');
    78   if( name == "" ) {
     66void DeclarationNode::print( std::ostream &os, int indent ) const {
     67    os << string(indent, ' ' );
     68    if ( name == "" ) {
    7969///     os << "An unnamed ";
    80   } else {
    81     os << name << ": a ";
    82   }
    83   if( linkage != LinkageSpec::Cforall ) {
    84     os << LinkageSpec::toString( linkage ) << " ";
    85   }
    86   printEnums( storageClasses.begin(), storageClasses.end(), storageClassName, os );
    87   if( type ) {
    88     type->print( os, indent );
    89   } else {
    90     os << "untyped entity ";
    91   }
    92   if( bitfieldWidth ) {
    93     os << endl << string(indent+2,  ' ') << "with bitfield width ";
    94     bitfieldWidth->printOneLine( os );
    95   }
    96 
    97   if( initializer != 0 ) {
    98     os << endl << string(indent+2,  ' ') << "with initializer ";
    99     initializer->printOneLine( os );
    100   }
    101 
    102   os << endl;
    103 }
    104 
    105 void
    106 DeclarationNode::printList( std::ostream &os, int indent ) const
    107 {
    108   ParseNode::printList( os, indent );
    109   if( hasEllipsis ) {
    110     os << string( indent, ' ' )  << "and a variable number of other arguments" << endl;
    111   }
    112 }
    113 
    114 DeclarationNode *
    115 DeclarationNode::newFunction( std::string* name, DeclarationNode *ret, DeclarationNode *param, StatementNode *body, bool newStyle )
    116 {
    117   DeclarationNode *newnode = new DeclarationNode;
    118   newnode->name = assign_strptr( name );
    119 
    120   newnode->type = new TypeData( TypeData::Function );
    121   newnode->type->function->params = param;
    122   newnode->type->function->newStyle = newStyle;
    123   newnode->type->function->body = body;
    124   if( body ) {
    125     newnode->type->function->hasBody = true;
    126   }
    127 
    128   if( ret ) {
    129     newnode->type->base = ret->type;
    130     ret->type = 0;
    131     delete ret;
    132   }
    133 
    134   return newnode;
    135 }
    136 
    137 DeclarationNode *
    138 DeclarationNode::newQualifier( Qualifier q )
    139 {
    140   DeclarationNode *newnode = new DeclarationNode;
    141   newnode->type = new TypeData();
    142   newnode->type->qualifiers.push_back( q );
    143   return newnode;
    144 }
    145 
    146 DeclarationNode *
    147 DeclarationNode::newStorageClass( StorageClass sc )
    148 {
    149   DeclarationNode *newnode = new DeclarationNode;
    150   newnode->storageClasses.push_back( sc );
    151   return newnode;
    152 }
    153 
    154 DeclarationNode *
    155 DeclarationNode::newBasicType( BasicType bt )
    156 {
    157   DeclarationNode *newnode = new DeclarationNode;
    158   newnode->type = new TypeData( TypeData::Basic );
    159   newnode->type->basic->typeSpec.push_back( bt );
    160   return newnode;
    161 }
    162 
    163 DeclarationNode *
    164 DeclarationNode::newModifier( Modifier mod )
    165 {
    166   DeclarationNode *newnode = new DeclarationNode;
    167   newnode->type = new TypeData( TypeData::Basic );
    168   newnode->type->basic->modifiers.push_back( mod );
    169   return newnode;
    170 }
    171 
    172 DeclarationNode *
    173 DeclarationNode::newForall( DeclarationNode* forall )
    174 {
    175   DeclarationNode *newnode = new DeclarationNode;
    176   newnode->type = new TypeData( TypeData::Unknown );
    177   newnode->type->forall = forall;
    178   return newnode;
    179 }
    180 
    181 DeclarationNode *
    182 DeclarationNode::newFromTypedef( std::string* name )
    183 {
    184   DeclarationNode *newnode = new DeclarationNode;
    185   newnode->type = new TypeData( TypeData::SymbolicInst );
    186   newnode->type->symbolic->name = assign_strptr( name );
    187   newnode->type->symbolic->isTypedef = true;
    188   newnode->type->symbolic->params = 0;
    189   return newnode;
    190 }
    191 
    192 DeclarationNode *
    193 DeclarationNode::newAggregate( TyCon kind, std::string* name, DeclarationNode *formals, ExpressionNode *actuals, DeclarationNode *fields )
    194 {
    195   DeclarationNode *newnode = new DeclarationNode;
    196   newnode->type = new TypeData( TypeData::Aggregate );
    197   newnode->type->aggregate->kind = kind;
    198   newnode->type->aggregate->name = assign_strptr( name );
    199   if( newnode->type->aggregate->name == "" ) {
    200     newnode->type->aggregate->name = DeclarationNode::anonymous.newName();
    201   }
    202   newnode->type->aggregate->params = formals;
    203   newnode->type->aggregate->actuals = actuals;
    204   newnode->type->aggregate->members = fields;
    205   return newnode;
    206 }
    207 
    208 DeclarationNode *
    209 DeclarationNode::newEnum( std::string *name, DeclarationNode *constants )
    210 {
    211   DeclarationNode *newnode = new DeclarationNode;
    212   newnode->name = assign_strptr( name );
    213   newnode->type = new TypeData( TypeData::Enum );
    214   newnode->type->enumeration->name = newnode->name;
    215   if( newnode->type->enumeration->name == "" ) {
    216     newnode->type->enumeration->name = DeclarationNode::anonymous.newName();
    217   }
    218   newnode->type->enumeration->constants = constants;
    219   return newnode;
    220 }
    221 
    222 DeclarationNode *
    223 DeclarationNode::newEnumConstant( std::string* name, ExpressionNode *constant )
    224 {
    225   DeclarationNode *newnode = new DeclarationNode;
    226   newnode->name = assign_strptr( name );
    227   // do something with the constant
    228   return newnode;
    229 }
    230 
    231 DeclarationNode *
    232 DeclarationNode::newName( std::string* name )
    233 {
    234   DeclarationNode *newnode = new DeclarationNode;
    235   newnode->name = assign_strptr( name );
    236   return newnode;
    237 }
    238 
    239 DeclarationNode *
    240 DeclarationNode::newFromTypeGen( std::string* name, ExpressionNode *params )
    241 {
    242   DeclarationNode *newnode = new DeclarationNode;
    243   newnode->type = new TypeData( TypeData::SymbolicInst );
    244   newnode->type->symbolic->name = assign_strptr( name );
    245   newnode->type->symbolic->isTypedef = false;
    246   newnode->type->symbolic->actuals = params;
    247   return newnode;
    248 }
    249 
    250 DeclarationNode *
    251 DeclarationNode::newTypeParam( TypeClass tc, std::string* name )
    252 {
    253   DeclarationNode *newnode = new DeclarationNode;
    254   newnode->name = assign_strptr( name );
    255   newnode->type = new TypeData( TypeData::Variable );
    256   newnode->type->variable->tyClass = tc;
    257   newnode->type->variable->name = newnode->name;
    258   return newnode;
    259 }
    260 
    261 DeclarationNode *
    262 DeclarationNode::newContext( std::string *name, DeclarationNode *params, DeclarationNode *asserts )
    263 {
    264   DeclarationNode *newnode = new DeclarationNode;
    265   newnode->type = new TypeData( TypeData::Aggregate );
    266   newnode->type->aggregate->kind = Context;
    267   newnode->type->aggregate->params = params;
    268   newnode->type->aggregate->members = asserts;
    269   newnode->type->aggregate->name = assign_strptr( name );
    270   return newnode;
    271 }
    272 
    273 DeclarationNode *
    274 DeclarationNode::newContextUse( std::string *name, ExpressionNode *params )
    275 {
    276   DeclarationNode *newnode = new DeclarationNode;
    277   newnode->type = new TypeData( TypeData::AggregateInst );
    278   newnode->type->aggInst->aggregate = new TypeData( TypeData::Aggregate );
    279   newnode->type->aggInst->aggregate->aggregate->kind = Context;
    280   newnode->type->aggInst->aggregate->aggregate->name = assign_strptr( name );
    281   newnode->type->aggInst->params = params;
    282   return newnode;
    283 }
    284 
    285 DeclarationNode *
    286 DeclarationNode::newTypeDecl( std::string *name, DeclarationNode *typeParams )
    287 {
    288   DeclarationNode *newnode = new DeclarationNode;
    289   newnode->name = assign_strptr( name );
    290   newnode->type = new TypeData( TypeData::Symbolic );
    291   newnode->type->symbolic->isTypedef = false;
    292   newnode->type->symbolic->params = typeParams;
    293   newnode->type->symbolic->name = newnode->name;
    294   return newnode;
    295 }
    296 
    297 DeclarationNode *
    298 DeclarationNode::newPointer( DeclarationNode *qualifiers )
    299 {
    300   DeclarationNode *newnode = new DeclarationNode;
    301   newnode->type = new TypeData( TypeData::Pointer );
    302   return newnode->addQualifiers( qualifiers );
    303 }
    304 
    305 DeclarationNode *
    306 DeclarationNode::newArray( ExpressionNode *size, DeclarationNode *qualifiers, bool isStatic )
    307 {
    308   DeclarationNode *newnode = new DeclarationNode;
    309   newnode->type = new TypeData( TypeData::Array );
    310   newnode->type->array->dimension = size;
    311   newnode->type->array->isStatic = isStatic;
    312   newnode->type->array->isVarLen = false;
    313   return newnode->addQualifiers( qualifiers );
    314 }
    315 
    316 DeclarationNode *
    317 DeclarationNode::newVarArray( DeclarationNode *qualifiers )
    318 {
    319   DeclarationNode *newnode = new DeclarationNode;
    320   newnode->type = new TypeData( TypeData::Array );
    321   newnode->type->array->dimension = 0;
    322   newnode->type->array->isStatic = false;
    323   newnode->type->array->isVarLen = true;
    324   return newnode->addQualifiers( qualifiers );
    325 }
    326 
    327 DeclarationNode *
    328 DeclarationNode::newBitfield( ExpressionNode *size )
    329 {
    330   DeclarationNode *newnode = new DeclarationNode;
    331   newnode->bitfieldWidth = size;
    332   return newnode;
    333 }
    334 
    335 DeclarationNode *
    336 DeclarationNode::newTuple( DeclarationNode *members )
    337 {
    338   DeclarationNode *newnode = new DeclarationNode;
    339   newnode->type = new TypeData( TypeData::Tuple );
    340   newnode->type->tuple->members = members;
    341   return newnode;
    342 }
    343 
    344 DeclarationNode *
    345 DeclarationNode::newTypeof( ExpressionNode *expr )
    346 {
    347   DeclarationNode *newnode = new DeclarationNode;
    348   newnode->type = new TypeData( TypeData::Typeof );
    349   newnode->type->typeexpr->expr = expr;
    350   return newnode;
    351 }
    352 
    353 DeclarationNode *
    354 DeclarationNode::newAttr( std::string *name, ExpressionNode *expr )
    355 {
    356   DeclarationNode *newnode = new DeclarationNode;
    357   newnode->type = new TypeData( TypeData::Attr );
    358   newnode->type->attr->name = assign_strptr( name );
    359   newnode->type->attr->expr = expr;
    360   return newnode;
    361 }
    362 
    363 DeclarationNode *
    364 DeclarationNode::newAttr( std::string *name, DeclarationNode *type )
    365 {
    366   DeclarationNode *newnode = new DeclarationNode;
    367   newnode->type = new TypeData( TypeData::Attr );
    368   newnode->type->attr->name = assign_strptr( name );
    369   newnode->type->attr->type = type;
    370   return newnode;
     70    } else {
     71        os << name << ": a ";
     72    }
     73
     74    if ( linkage != LinkageSpec::Cforall ) {
     75        os << LinkageSpec::toString( linkage ) << " ";
     76    }
     77
     78    printEnums( storageClasses.begin(), storageClasses.end(), storageClassName, os );
     79    if ( type ) {
     80        type->print( os, indent );
     81    } else {
     82        os << "untyped entity ";
     83    }
     84
     85    if ( bitfieldWidth ) {
     86        os << endl << string(indent+2,  ' ') << "with bitfield width ";
     87        bitfieldWidth->printOneLine( os );
     88    }
     89
     90    if ( initializer != 0 ) {
     91        os << endl << string(indent+2,  ' ') << "with initializer ";
     92        initializer->printOneLine( os );
     93    }
     94
     95    os << endl;
     96}
     97
     98void DeclarationNode::printList( std::ostream &os, int indent ) const {
     99    ParseNode::printList( os, indent );
     100    if ( hasEllipsis ) {
     101        os << string( indent, ' ' )  << "and a variable number of other arguments" << endl;
     102    }
     103}
     104
     105DeclarationNode *DeclarationNode::newFunction( std::string* name, DeclarationNode *ret, DeclarationNode *param, StatementNode *body, bool newStyle ) {
     106    DeclarationNode *newnode = new DeclarationNode;
     107    newnode->name = assign_strptr( name );
     108
     109    newnode->type = new TypeData( TypeData::Function );
     110    newnode->type->function->params = param;
     111    newnode->type->function->newStyle = newStyle;
     112    newnode->type->function->body = body;
     113
     114    if ( body ) {
     115        newnode->type->function->hasBody = true;
     116    }
     117
     118    if ( ret ) {
     119        newnode->type->base = ret->type;
     120        ret->type = 0;
     121        delete ret;
     122    }
     123
     124    return newnode;
     125}
     126
     127DeclarationNode *DeclarationNode::newQualifier( Qualifier q ) {
     128    DeclarationNode *newnode = new DeclarationNode;
     129    newnode->type = new TypeData();
     130    newnode->type->qualifiers.push_back( q );
     131    return newnode;
     132}
     133
     134DeclarationNode *DeclarationNode::newStorageClass( StorageClass sc ) {
     135    DeclarationNode *newnode = new DeclarationNode;
     136    newnode->storageClasses.push_back( sc );
     137    return newnode;
     138}
     139
     140DeclarationNode *DeclarationNode::newBasicType( BasicType bt ) {
     141    DeclarationNode *newnode = new DeclarationNode;
     142    newnode->type = new TypeData( TypeData::Basic );
     143    newnode->type->basic->typeSpec.push_back( bt );
     144    return newnode;
     145}
     146
     147DeclarationNode *DeclarationNode::newModifier( Modifier mod ) {
     148    DeclarationNode *newnode = new DeclarationNode;
     149    newnode->type = new TypeData( TypeData::Basic );
     150    newnode->type->basic->modifiers.push_back( mod );
     151    return newnode;
     152}
     153
     154DeclarationNode *DeclarationNode::newForall( DeclarationNode* forall ) {
     155    DeclarationNode *newnode = new DeclarationNode;
     156    newnode->type = new TypeData( TypeData::Unknown );
     157    newnode->type->forall = forall;
     158    return newnode;
     159}
     160
     161DeclarationNode *DeclarationNode::newFromTypedef( std::string* name ) {
     162    DeclarationNode *newnode = new DeclarationNode;
     163    newnode->type = new TypeData( TypeData::SymbolicInst );
     164    newnode->type->symbolic->name = assign_strptr( name );
     165    newnode->type->symbolic->isTypedef = true;
     166    newnode->type->symbolic->params = 0;
     167    return newnode;
     168}
     169
     170DeclarationNode *DeclarationNode::newAggregate( TyCon kind, std::string* name, DeclarationNode *formals, ExpressionNode *actuals, DeclarationNode *fields ) {
     171    DeclarationNode *newnode = new DeclarationNode;
     172    newnode->type = new TypeData( TypeData::Aggregate );
     173    newnode->type->aggregate->kind = kind;
     174    newnode->type->aggregate->name = assign_strptr( name );
     175    if ( newnode->type->aggregate->name == "" ) {
     176        newnode->type->aggregate->name = DeclarationNode::anonymous.newName();
     177    }
     178    newnode->type->aggregate->params = formals;
     179    newnode->type->aggregate->actuals = actuals;
     180    newnode->type->aggregate->members = fields;
     181    return newnode;
     182}
     183
     184DeclarationNode *DeclarationNode::newEnum( std::string *name, DeclarationNode *constants ) {
     185    DeclarationNode *newnode = new DeclarationNode;
     186    newnode->name = assign_strptr( name );
     187    newnode->type = new TypeData( TypeData::Enum );
     188    newnode->type->enumeration->name = newnode->name;
     189    if ( newnode->type->enumeration->name == "" ) {
     190        newnode->type->enumeration->name = DeclarationNode::anonymous.newName();
     191    }
     192    newnode->type->enumeration->constants = constants;
     193    return newnode;
     194}
     195
     196DeclarationNode *DeclarationNode::newEnumConstant( std::string* name, ExpressionNode *constant ) {
     197    DeclarationNode *newnode = new DeclarationNode;
     198    newnode->name = assign_strptr( name );
     199    // do something with the constant
     200    return newnode;
     201}
     202
     203DeclarationNode *DeclarationNode::newName( std::string* name ) {
     204    DeclarationNode *newnode = new DeclarationNode;
     205    newnode->name = assign_strptr( name );
     206    return newnode;
     207}
     208
     209DeclarationNode *DeclarationNode::newFromTypeGen( std::string* name, ExpressionNode *params ) {
     210    DeclarationNode *newnode = new DeclarationNode;
     211    newnode->type = new TypeData( TypeData::SymbolicInst );
     212    newnode->type->symbolic->name = assign_strptr( name );
     213    newnode->type->symbolic->isTypedef = false;
     214    newnode->type->symbolic->actuals = params;
     215    return newnode;
     216}
     217
     218DeclarationNode *DeclarationNode::newTypeParam( TypeClass tc, std::string* name ) {
     219    DeclarationNode *newnode = new DeclarationNode;
     220    newnode->name = assign_strptr( name );
     221    newnode->type = new TypeData( TypeData::Variable );
     222    newnode->type->variable->tyClass = tc;
     223    newnode->type->variable->name = newnode->name;
     224    return newnode;
     225}
     226
     227DeclarationNode *DeclarationNode::newContext( std::string *name, DeclarationNode *params, DeclarationNode *asserts ) {
     228    DeclarationNode *newnode = new DeclarationNode;
     229    newnode->type = new TypeData( TypeData::Aggregate );
     230    newnode->type->aggregate->kind = Context;
     231    newnode->type->aggregate->params = params;
     232    newnode->type->aggregate->members = asserts;
     233    newnode->type->aggregate->name = assign_strptr( name );
     234    return newnode;
     235}
     236
     237DeclarationNode *DeclarationNode::newContextUse( std::string *name, ExpressionNode *params ) {
     238    DeclarationNode *newnode = new DeclarationNode;
     239    newnode->type = new TypeData( TypeData::AggregateInst );
     240    newnode->type->aggInst->aggregate = new TypeData( TypeData::Aggregate );
     241    newnode->type->aggInst->aggregate->aggregate->kind = Context;
     242    newnode->type->aggInst->aggregate->aggregate->name = assign_strptr( name );
     243    newnode->type->aggInst->params = params;
     244    return newnode;
     245}
     246
     247DeclarationNode *DeclarationNode::newTypeDecl( std::string *name, DeclarationNode *typeParams ) {
     248    DeclarationNode *newnode = new DeclarationNode;
     249    newnode->name = assign_strptr( name );
     250    newnode->type = new TypeData( TypeData::Symbolic );
     251    newnode->type->symbolic->isTypedef = false;
     252    newnode->type->symbolic->params = typeParams;
     253    newnode->type->symbolic->name = newnode->name;
     254    return newnode;
     255}
     256
     257DeclarationNode *DeclarationNode::newPointer( DeclarationNode *qualifiers ) {
     258    DeclarationNode *newnode = new DeclarationNode;
     259    newnode->type = new TypeData( TypeData::Pointer );
     260    return newnode->addQualifiers( qualifiers );
     261}
     262
     263DeclarationNode *DeclarationNode::newArray( ExpressionNode *size, DeclarationNode *qualifiers, bool isStatic ) {
     264    DeclarationNode *newnode = new DeclarationNode;
     265    newnode->type = new TypeData( TypeData::Array );
     266    newnode->type->array->dimension = size;
     267    newnode->type->array->isStatic = isStatic;
     268    newnode->type->array->isVarLen = false;
     269    return newnode->addQualifiers( qualifiers );
     270}
     271
     272DeclarationNode *DeclarationNode::newVarArray( DeclarationNode *qualifiers ) {
     273    DeclarationNode *newnode = new DeclarationNode;
     274    newnode->type = new TypeData( TypeData::Array );
     275    newnode->type->array->dimension = 0;
     276    newnode->type->array->isStatic = false;
     277    newnode->type->array->isVarLen = true;
     278    return newnode->addQualifiers( qualifiers );
     279}
     280
     281DeclarationNode *DeclarationNode::newBitfield( ExpressionNode *size ) {
     282    DeclarationNode *newnode = new DeclarationNode;
     283    newnode->bitfieldWidth = size;
     284    return newnode;
     285}
     286
     287DeclarationNode *DeclarationNode::newTuple( DeclarationNode *members ) {
     288    DeclarationNode *newnode = new DeclarationNode;
     289    newnode->type = new TypeData( TypeData::Tuple );
     290    newnode->type->tuple->members = members;
     291    return newnode;
     292}
     293
     294DeclarationNode *DeclarationNode::newTypeof( ExpressionNode *expr ) {
     295    DeclarationNode *newnode = new DeclarationNode;
     296    newnode->type = new TypeData( TypeData::Typeof );
     297    newnode->type->typeexpr->expr = expr;
     298    return newnode;
     299}
     300
     301DeclarationNode *DeclarationNode::newAttr( std::string *name, ExpressionNode *expr ) {
     302    DeclarationNode *newnode = new DeclarationNode;
     303    newnode->type = new TypeData( TypeData::Attr );
     304    newnode->type->attr->name = assign_strptr( name );
     305    newnode->type->attr->expr = expr;
     306    return newnode;
     307}
     308
     309DeclarationNode *DeclarationNode::newAttr( std::string *name, DeclarationNode *type ) {
     310    DeclarationNode *newnode = new DeclarationNode;
     311    newnode->type = new TypeData( TypeData::Attr );
     312    newnode->type->attr->name = assign_strptr( name );
     313    newnode->type->attr->type = type;
     314    return newnode;
     315}
     316
     317static void addQualifiersToType( TypeData *&src, TypeData *dst ) {
     318    if ( src && dst ) {
     319        if ( src->forall && dst->kind == TypeData::Function ) {
     320            if ( dst->forall ) {
     321                dst->forall->appendList( src->forall );
     322            } else {
     323                dst->forall = src->forall;
     324            }
     325            src->forall = 0;
     326        }
     327        if ( dst->base ) {
     328            addQualifiersToType( src, dst->base );
     329        } else if ( dst->kind == TypeData::Function ) {
     330            dst->base = src;
     331            src = 0;
     332        } else {
     333            dst->qualifiers.splice( dst->qualifiers.end(), src->qualifiers );
     334        }
     335    }
     336}
     337     
     338DeclarationNode *DeclarationNode::addQualifiers( DeclarationNode *q ) {
     339    if ( q ) {
     340        storageClasses.splice( storageClasses.end(), q->storageClasses );
     341        if ( q->type ) {
     342            if ( ! type ) {
     343                type = new TypeData;
     344            }
     345            addQualifiersToType( q->type, type );
     346            if ( q->type && q->type->forall ) {
     347                if ( type->forall ) {
     348                    type->forall->appendList( q->type->forall );
     349                } else {
     350                    type->forall = q->type->forall;
     351                }
     352                q->type->forall = 0;
     353            }
     354        }
     355    }
     356    delete q;
     357    return this;
     358}
     359
     360DeclarationNode *DeclarationNode::copyStorageClasses( DeclarationNode *q ) {
     361    storageClasses = q->storageClasses;
     362    return this;
     363}
     364
     365static void addTypeToType( TypeData *&src, TypeData *&dst ) {
     366    if ( src && dst ) {
     367        if ( src->forall && dst->kind == TypeData::Function ) {
     368            if ( dst->forall ) {
     369                dst->forall->appendList( src->forall );
     370            } else {
     371                dst->forall = src->forall;
     372            }
     373            src->forall = 0;
     374        }
     375        if ( dst->base ) {
     376            addTypeToType( src, dst->base );
     377        } else {
     378            switch ( dst->kind ) {
     379              case TypeData::Unknown:
     380                src->qualifiers.splice( src->qualifiers.end(), dst->qualifiers );
     381                dst = src;
     382                src = 0;
     383                break;
     384
     385              case TypeData::Basic:
     386                dst->qualifiers.splice( dst->qualifiers.end(), src->qualifiers );
     387                if ( src->kind != TypeData::Unknown ) {
     388                    assert( src->kind == TypeData::Basic );
     389                    dst->basic->modifiers.splice( dst->basic->modifiers.end(), src->basic->modifiers );
     390                    dst->basic->typeSpec.splice( dst->basic->typeSpec.end(), src->basic->typeSpec );
     391                }
     392                break;
     393
     394              default:
     395                switch ( src->kind ) {
     396                  case TypeData::Aggregate:
     397                  case TypeData::Enum:
     398                    dst->base = new TypeData( TypeData::AggregateInst );
     399                    dst->base->aggInst->aggregate = src;
     400                    if ( src->kind == TypeData::Aggregate ) {
     401                        dst->base->aggInst->params = maybeClone( src->aggregate->actuals );
     402                    }
     403                    dst->base->qualifiers.splice( dst->base->qualifiers.end(), src->qualifiers );
     404                    src = 0;
     405                    break;
     406         
     407                  default:
     408                    if ( dst->forall ) {
     409                        dst->forall->appendList( src->forall );
     410                    } else {
     411                        dst->forall = src->forall;
     412                    }
     413                    src->forall = 0;
     414                    dst->base = src;
     415                    src = 0;
     416                }
     417            }
     418        }
     419    }
     420}
     421
     422DeclarationNode *DeclarationNode::addType( DeclarationNode *o ) {
     423    if ( o ) {
     424        storageClasses.splice( storageClasses.end(), o->storageClasses );
     425        if ( o->type ) {
     426            if ( ! type ) {
     427                if ( o->type->kind == TypeData::Aggregate || o->type->kind == TypeData::Enum ) {
     428                    type = new TypeData( TypeData::AggregateInst );
     429                    type->aggInst->aggregate = o->type;
     430                    if ( o->type->kind == TypeData::Aggregate ) {
     431                        type->aggInst->params = maybeClone( o->type->aggregate->actuals );
     432                    }
     433                    type->qualifiers.splice( type->qualifiers.end(), o->type->qualifiers );
     434                } else {
     435                    type = o->type;
     436                }
     437                o->type = 0;
     438            } else {
     439                addTypeToType( o->type, type );
     440            }
     441        }
     442        if ( o->bitfieldWidth ) {
     443            bitfieldWidth = o->bitfieldWidth;
     444        }
     445    }
     446    delete o;
     447    return this;
     448}
     449
     450DeclarationNode *DeclarationNode::addTypedef() {
     451    TypeData *newtype = new TypeData( TypeData::Symbolic );
     452    newtype->symbolic->params = 0;
     453    newtype->symbolic->isTypedef = true;
     454    newtype->symbolic->name = name;
     455    newtype->base = type;
     456    type = newtype;
     457    return this;
     458}
     459
     460DeclarationNode *DeclarationNode::addAssertions( DeclarationNode* assertions ) {
     461    assert( type );
     462    switch ( type->kind ) {
     463      case TypeData::Symbolic:
     464        if ( type->symbolic->assertions ) {
     465            type->symbolic->assertions->appendList( assertions );
     466        } else {
     467            type->symbolic->assertions = assertions;
     468        }
     469        break;
     470   
     471      case TypeData::Variable:
     472        if ( type->variable->assertions ) {
     473            type->variable->assertions->appendList( assertions );
     474        } else {
     475            type->variable->assertions = assertions;
     476        }
     477        break;
     478   
     479      default:
     480        assert( false );
     481    }
     482   
     483    return this;
     484}
     485
     486DeclarationNode *DeclarationNode::addName( std::string* newname ) {
     487    name = assign_strptr( newname );
     488    return this;
     489}
     490
     491DeclarationNode *DeclarationNode::addBitfield( ExpressionNode *size ) {
     492    bitfieldWidth = size;
     493    return this;
     494}
     495
     496DeclarationNode *DeclarationNode::addVarArgs() {
     497    assert( type );
     498    hasEllipsis = true;
     499    return this;
     500}
     501
     502DeclarationNode *DeclarationNode::addFunctionBody( StatementNode *body ) {
     503    assert( type );
     504    assert( type->kind == TypeData::Function );
     505    assert( type->function->body == 0 );
     506    type->function->body = body;
     507    type->function->hasBody = true;
     508    return this;
     509}
     510
     511DeclarationNode *DeclarationNode::addOldDeclList( DeclarationNode *list ) {
     512    assert( type );
     513    assert( type->kind == TypeData::Function );
     514    assert( type->function->oldDeclList == 0 );
     515    type->function->oldDeclList = list;
     516    return this;
    371517}
    372518
    373519static void
    374 addQualifiersToType( TypeData *&src, TypeData *dst )
    375 {
    376   if( src && dst ) {
    377     if( src->forall && dst->kind == TypeData::Function ) {
    378       if( dst->forall ) {
    379         dst->forall->appendList( src->forall );
    380       } else {
    381         dst->forall = src->forall;
    382       }
    383       src->forall = 0;
    384     }
    385     if( dst->base ) {
    386       addQualifiersToType( src, dst->base );
    387     } else if( dst->kind == TypeData::Function ) {
    388       dst->base = src;
    389       src = 0;
     520setBase( TypeData *&type, TypeData *newType ) {
     521    if ( type ) {
     522        TypeData *prevBase = type;
     523        TypeData *curBase = type->base;
     524        while( curBase != 0 ) {
     525            prevBase = curBase;
     526            curBase = curBase->base;
     527        }
     528        prevBase->base = newType;
    390529    } else {
    391       dst->qualifiers.splice( dst->qualifiers.end(), src->qualifiers );
    392     }
    393   }
    394 }
    395      
    396 DeclarationNode *
    397 DeclarationNode::addQualifiers( DeclarationNode *q )
    398 {
    399   if( q ) {
    400     storageClasses.splice( storageClasses.end(), q->storageClasses );
    401     if( q->type ) {
    402       if( !type ) {
    403         type = new TypeData;
    404       }
    405       addQualifiersToType( q->type, type );
    406       if( q->type && q->type->forall ) {
    407         if( type->forall ) {
    408           type->forall->appendList( q->type->forall );
    409         } else {
    410           type->forall = q->type->forall;
    411         }
    412         q->type->forall = 0;
    413       }
    414     }
    415   }
    416   delete q;
    417   return this;
    418 }
    419 
    420 DeclarationNode *
    421 DeclarationNode::copyStorageClasses( DeclarationNode *q )
    422 {
    423   storageClasses = q->storageClasses;
    424   return this;
    425 }
    426 
    427 static void
    428 addTypeToType( TypeData *&src, TypeData *&dst )
    429 {
    430   if( src && dst ) {
    431     if( src->forall && dst->kind == TypeData::Function ) {
    432       if( dst->forall ) {
    433         dst->forall->appendList( src->forall );
    434       } else {
    435         dst->forall = src->forall;
    436       }
    437       src->forall = 0;
    438     }
    439     if( dst->base ) {
    440       addTypeToType( src, dst->base );
     530        type = newType;
     531    }
     532}
     533
     534DeclarationNode *DeclarationNode::addPointer( DeclarationNode *p ) {
     535    if ( p ) {
     536        assert( p->type->kind == TypeData::Pointer );
     537        setBase( type, p->type );
     538        p->type = 0;
     539        delete p;
     540    }
     541    return this;
     542}
     543
     544DeclarationNode *DeclarationNode::addArray( DeclarationNode *a ) {
     545    if ( a ) {
     546        assert( a->type->kind == TypeData::Array );
     547        setBase( type, a->type );
     548        a->type = 0;
     549        delete a;
     550    }
     551    return this;
     552}
     553
     554DeclarationNode *DeclarationNode::addNewPointer( DeclarationNode *p ) {
     555    if ( p ) {
     556        assert( p->type->kind == TypeData::Pointer );
     557        if ( type ) {
     558            switch ( type->kind ) {
     559              case TypeData::Aggregate:
     560              case TypeData::Enum:
     561                p->type->base = new TypeData( TypeData::AggregateInst );
     562                p->type->base->aggInst->aggregate = type;
     563                if ( type->kind == TypeData::Aggregate ) {
     564                    p->type->base->aggInst->params = maybeClone( type->aggregate->actuals );
     565                }
     566                p->type->base->qualifiers.splice( p->type->base->qualifiers.end(), type->qualifiers );
     567                break;
     568       
     569              default:
     570                p->type->base = type;
     571            }
     572            type = 0;
     573        }
     574        delete this;
     575        return p;
    441576    } else {
    442       switch( dst->kind ) {
    443       case TypeData::Unknown:
    444         src->qualifiers.splice( src->qualifiers.end(), dst->qualifiers );
    445         dst = src;
    446         src = 0;
    447         break;
    448 
    449       case TypeData::Basic:
    450         dst->qualifiers.splice( dst->qualifiers.end(), src->qualifiers );
    451         if( src->kind != TypeData::Unknown ) {
    452           assert( src->kind == TypeData::Basic );
    453           dst->basic->modifiers.splice( dst->basic->modifiers.end(), src->basic->modifiers );
    454           dst->basic->typeSpec.splice( dst->basic->typeSpec.end(), src->basic->typeSpec );
    455         }
    456         break;
    457 
    458       default:
    459         switch( src->kind ) {
    460         case TypeData::Aggregate:
    461         case TypeData::Enum:
    462           dst->base = new TypeData( TypeData::AggregateInst );
    463           dst->base->aggInst->aggregate = src;
    464           if( src->kind == TypeData::Aggregate ) {
    465             dst->base->aggInst->params = maybeClone( src->aggregate->actuals );
    466           }
    467           dst->base->qualifiers.splice( dst->base->qualifiers.end(), src->qualifiers );
    468           src = 0;
    469           break;
    470          
    471         default:
    472           if( dst->forall ) {
    473             dst->forall->appendList( src->forall );
    474           } else {
    475             dst->forall = src->forall;
    476           }
    477           src->forall = 0;
    478           dst->base = src;
    479           src = 0;
    480         }
    481       }
    482     }
    483   }
    484 }
    485 
    486 DeclarationNode *
    487 DeclarationNode::addType( DeclarationNode *o )
    488 {
    489   if( o ) {
    490     storageClasses.splice( storageClasses.end(), o->storageClasses );
    491     if ( o->type ) {
    492       if( !type ) {
    493         if( o->type->kind == TypeData::Aggregate || o->type->kind == TypeData::Enum ) {
    494           type = new TypeData( TypeData::AggregateInst );
    495           type->aggInst->aggregate = o->type;
    496           if( o->type->kind == TypeData::Aggregate ) {
    497             type->aggInst->params = maybeClone( o->type->aggregate->actuals );
    498           }
    499           type->qualifiers.splice( type->qualifiers.end(), o->type->qualifiers );
     577        return this;
     578    }
     579}
     580
     581static TypeData *findLast( TypeData *a ) {
     582    assert( a );
     583    TypeData *cur = a;
     584    while( cur->base ) {
     585        cur = cur->base;
     586    }
     587    return cur;
     588}
     589
     590DeclarationNode *DeclarationNode::addNewArray( DeclarationNode *a ) {
     591    if ( a ) {
     592        assert( a->type->kind == TypeData::Array );
     593        TypeData *lastArray = findLast( a->type );
     594        if ( type ) { 
     595            switch ( type->kind ) {
     596              case TypeData::Aggregate:
     597              case TypeData::Enum:
     598                lastArray->base = new TypeData( TypeData::AggregateInst );
     599                lastArray->base->aggInst->aggregate = type;
     600                if ( type->kind == TypeData::Aggregate ) {
     601                    lastArray->base->aggInst->params = maybeClone( type->aggregate->actuals );
     602                }
     603                lastArray->base->qualifiers.splice( lastArray->base->qualifiers.end(), type->qualifiers );
     604                break;
     605       
     606              default:
     607                lastArray->base = type;
     608            }
     609            type = 0;
     610        }
     611        delete this;
     612        return a;
     613    } else {
     614        return this;
     615    }
     616}
     617
     618DeclarationNode *DeclarationNode::addParamList( DeclarationNode *params ) {
     619    TypeData *ftype = new TypeData( TypeData::Function );
     620    ftype->function->params = params;
     621    setBase( type, ftype );
     622    return this;
     623}
     624
     625static TypeData *addIdListToType( TypeData *type, DeclarationNode *ids ) {
     626    if ( type ) {
     627        if ( type->kind != TypeData::Function ) {
     628            type->base = addIdListToType( type->base, ids );
    500629        } else {
    501           type = o->type;
    502         }
    503         o->type = 0;
    504       } else {
    505         addTypeToType( o->type, type );
    506       }
    507     }
    508     if( o->bitfieldWidth ) {
    509       bitfieldWidth = o->bitfieldWidth;
    510     }
    511   }
    512   delete o;
    513   return this;
    514 }
    515 
    516 DeclarationNode *
    517 DeclarationNode::addTypedef()
    518 {
    519   TypeData *newtype = new TypeData( TypeData::Symbolic );
    520   newtype->symbolic->params = 0;
    521   newtype->symbolic->isTypedef = true;
    522   newtype->symbolic->name = name;
    523   newtype->base = type;
    524   type = newtype;
    525   return this;
    526 }
    527 
    528 DeclarationNode *
    529 DeclarationNode::addAssertions( DeclarationNode* assertions )
    530 {
    531   assert( type );
    532   switch( type->kind ) {
    533   case TypeData::Symbolic:
    534     if( type->symbolic->assertions ) {
    535       type->symbolic->assertions->appendList( assertions );
     630            type->function->idList = ids;
     631        }
     632        return type;
    536633    } else {
    537       type->symbolic->assertions = assertions;
    538     }
    539     break;
     634        TypeData *newtype = new TypeData( TypeData::Function );
     635        newtype->function->idList = ids;
     636        return newtype;
     637    }
     638}
    540639   
    541   case TypeData::Variable:
    542     if( type->variable->assertions ) {
    543       type->variable->assertions->appendList( assertions );
     640DeclarationNode *DeclarationNode::addIdList( DeclarationNode *ids ) {
     641    type = addIdListToType( type, ids );
     642    return this;
     643}
     644
     645DeclarationNode *DeclarationNode::addInitializer( InitializerNode *init ) {
     646    //assert
     647    initializer = init;
     648    return this;
     649}
     650
     651DeclarationNode *DeclarationNode::cloneBaseType( string *newName ) {
     652    DeclarationNode *newnode = new DeclarationNode;
     653    TypeData *srcType = type;
     654    while( srcType->base ) {
     655        srcType = srcType->base;
     656    }
     657    newnode->type = maybeClone( srcType );
     658    if ( newnode->type->kind == TypeData::AggregateInst ) {
     659        // don't duplicate members
     660        if ( newnode->type->aggInst->aggregate->kind == TypeData::Enum ) {
     661            delete newnode->type->aggInst->aggregate->enumeration->constants;
     662            newnode->type->aggInst->aggregate->enumeration->constants = 0;
     663        } else {
     664            assert( newnode->type->aggInst->aggregate->kind == TypeData::Aggregate );
     665            delete newnode->type->aggInst->aggregate->aggregate->members;
     666            newnode->type->aggInst->aggregate->aggregate->members = 0;
     667        }
     668    }
     669    newnode->type->forall = maybeClone( type->forall );
     670    newnode->storageClasses = storageClasses;
     671    newnode->name = assign_strptr( newName );
     672    return newnode;
     673}
     674
     675DeclarationNode *DeclarationNode::cloneBaseType( DeclarationNode *o ) {
     676    if ( o ) {
     677        o->storageClasses.insert( o->storageClasses.end(), storageClasses.begin(), storageClasses.end() );
     678        if ( type ) {
     679            TypeData *srcType = type;
     680            while( srcType->base ) {
     681                srcType = srcType->base;
     682            }
     683            TypeData *newType = srcType->clone();
     684            if ( newType->kind == TypeData::AggregateInst ) {
     685                // don't duplicate members
     686                if ( newType->aggInst->aggregate->kind == TypeData::Enum ) {
     687                    delete newType->aggInst->aggregate->enumeration->constants;
     688                    newType->aggInst->aggregate->enumeration->constants = 0;
     689                } else {
     690                    assert( newType->aggInst->aggregate->kind == TypeData::Aggregate );
     691                    delete newType->aggInst->aggregate->aggregate->members;
     692                    newType->aggInst->aggregate->aggregate->members = 0;
     693                }
     694            }
     695            newType->forall = maybeClone( type->forall );
     696            if ( ! o->type ) {
     697                o->type = newType;
     698            } else {
     699                addTypeToType( newType, o->type );
     700                delete newType;
     701            }
     702        }
     703    }
     704    return o;
     705}
     706
     707DeclarationNode *DeclarationNode::cloneType( string *newName ) {
     708    DeclarationNode *newnode = new DeclarationNode;
     709    newnode->type = maybeClone( type );
     710    newnode->storageClasses = storageClasses;
     711    newnode->name = assign_strptr( newName );
     712    return newnode;
     713}
     714
     715DeclarationNode *DeclarationNode::cloneType( DeclarationNode *o ) {
     716    if ( o ) {
     717        o->storageClasses.insert( o->storageClasses.end(), storageClasses.begin(), storageClasses.end() );
     718        if ( type ) {
     719            TypeData *newType = type->clone();
     720            if ( ! o->type ) {
     721                o->type = newType;
     722            } else {
     723                addTypeToType( newType, o->type );
     724                delete newType;
     725            }
     726        }
     727    }
     728    return o;
     729}
     730
     731DeclarationNode *DeclarationNode::appendList( DeclarationNode *node ) {
     732    if ( node != 0 ) {
     733        set_link( node );
     734    }
     735    return this;
     736}
     737
     738DeclarationNode *DeclarationNode::extractAggregate() const {
     739    if ( type ) {
     740        TypeData *ret = type->extractAggregate();
     741        if ( ret ) {
     742            DeclarationNode *newnode = new DeclarationNode;
     743            newnode->type = ret;
     744            return newnode;
     745        } else {
     746            return 0;
     747        }
    544748    } else {
    545       type->variable->assertions = assertions;
    546     }
    547     break;
    548    
    549   default:
    550     assert( false );
    551   }
    552    
    553   return this;
    554 }
    555 
    556 DeclarationNode *
    557 DeclarationNode::addName( std::string* newname )
    558 {
    559   name = assign_strptr( newname );
    560   return this;
    561 }
    562 
    563 DeclarationNode *
    564 DeclarationNode::addBitfield( ExpressionNode *size )
    565 {
    566   bitfieldWidth = size;
    567   return this;
    568 }
    569 
    570 DeclarationNode *
    571 DeclarationNode::addVarArgs()
    572 {
    573   assert( type );
    574   hasEllipsis = true;
    575   return this;
    576 }
    577 
    578 DeclarationNode *
    579 DeclarationNode::addFunctionBody( StatementNode *body )
    580 {
    581   assert( type );
    582   assert( type->kind == TypeData::Function );
    583   assert( type->function->body == 0 );
    584   type->function->body = body;
    585   type->function->hasBody = true;
    586   return this;
    587 }
    588 
    589 DeclarationNode *
    590 DeclarationNode::addOldDeclList( DeclarationNode *list )
    591 {
    592   assert( type );
    593   assert( type->kind == TypeData::Function );
    594   assert( type->function->oldDeclList == 0 );
    595   type->function->oldDeclList = list;
    596   return this;
    597 }
    598 
    599 static void
    600 setBase( TypeData *&type, TypeData *newType )
    601 {
    602   if( type ) {
    603     TypeData *prevBase = type;
    604     TypeData *curBase = type->base;
    605     while( curBase != 0 ) {
    606       prevBase = curBase;
    607       curBase = curBase->base;
    608     }
    609     prevBase->base = newType;
    610   } else {
    611     type = newType;
    612   }
    613 }
    614 
    615 DeclarationNode *
    616 DeclarationNode::addPointer( DeclarationNode *p )
    617 {
    618   if( p ) {
    619     assert( p->type->kind == TypeData::Pointer );
    620     setBase( type, p->type );
    621     p->type = 0;
    622     delete p;
    623   }
    624   return this;
    625 }
    626 
    627 DeclarationNode *
    628 DeclarationNode::addArray( DeclarationNode *a )
    629 {
    630   if( a ) {
    631     assert( a->type->kind == TypeData::Array );
    632     setBase( type, a->type );
    633     a->type = 0;
    634     delete a;
    635   }
    636   return this;
    637 }
    638 
    639 DeclarationNode *
    640 DeclarationNode::addNewPointer( DeclarationNode *p )
    641 {
    642   if( p ) {
    643     assert( p->type->kind == TypeData::Pointer );
    644     if( type ) {
    645       switch( type->kind ) {
    646       case TypeData::Aggregate:
    647       case TypeData::Enum:
    648         p->type->base = new TypeData( TypeData::AggregateInst );
    649         p->type->base->aggInst->aggregate = type;
    650         if( type->kind == TypeData::Aggregate ) {
    651           p->type->base->aggInst->params = maybeClone( type->aggregate->actuals );
    652         }
    653         p->type->base->qualifiers.splice( p->type->base->qualifiers.end(), type->qualifiers );
    654         break;
    655        
    656       default:
    657         p->type->base = type;
    658       }
    659       type = 0;
    660     }
    661     delete this;
    662     return p;
    663   } else {
    664     return this;
    665   }
    666 }
    667 
    668 static TypeData *
    669 findLast( TypeData *a )
    670 {
    671   assert( a );
    672   TypeData *cur = a;
    673   while( cur->base ) {
    674     cur = cur->base;
    675   }
    676   return cur;
    677 }
    678 
    679 DeclarationNode *
    680 DeclarationNode::addNewArray( DeclarationNode *a )
    681 {
    682   if( a ) {
    683     assert( a->type->kind == TypeData::Array );
    684     TypeData *lastArray = findLast( a->type );
    685     if( type ) { 
    686       switch( type->kind ) {
    687       case TypeData::Aggregate:
    688       case TypeData::Enum:
    689         lastArray->base = new TypeData( TypeData::AggregateInst );
    690         lastArray->base->aggInst->aggregate = type;
    691         if( type->kind == TypeData::Aggregate ) {
    692           lastArray->base->aggInst->params = maybeClone( type->aggregate->actuals );
    693         }
    694         lastArray->base->qualifiers.splice( lastArray->base->qualifiers.end(), type->qualifiers );
    695         break;
    696        
    697       default:
    698         lastArray->base = type;
    699       }
    700       type = 0;
    701     }
    702     delete this;
    703     return a;
    704   } else {
    705     return this;
    706   }
    707 }
    708 
    709 DeclarationNode *
    710 DeclarationNode::addParamList( DeclarationNode *params )
    711 {
    712   TypeData *ftype = new TypeData( TypeData::Function );
    713   ftype->function->params = params;
    714   setBase( type, ftype );
    715   return this;
    716 }
    717 
    718 static TypeData*
    719 addIdListToType( TypeData *type, DeclarationNode *ids )
    720 {
    721   if( type ) {
    722     if( type->kind != TypeData::Function ) {
    723       type->base = addIdListToType( type->base, ids );
    724     } else {
    725       type->function->idList = ids;
    726     }
    727     return type;
    728   } else {
    729     TypeData *newtype = new TypeData( TypeData::Function );
    730     newtype->function->idList = ids;
    731     return newtype;
    732   }
    733 }
    734    
    735 DeclarationNode *
    736 DeclarationNode::addIdList( DeclarationNode *ids )
    737 {
    738   type = addIdListToType( type, ids );
    739   return this;
    740 }
    741 
    742 DeclarationNode *
    743 DeclarationNode::addInitializer( InitializerNode *init )
    744 {
    745   //assert
    746   initializer = init;
    747   return this;
    748 }
    749 
    750 DeclarationNode *
    751 DeclarationNode::cloneBaseType( string *newName )
    752 {
    753   DeclarationNode *newnode = new DeclarationNode;
    754   TypeData *srcType = type;
    755   while( srcType->base ) {
    756     srcType = srcType->base;
    757   }
    758   newnode->type = maybeClone( srcType );
    759   if( newnode->type->kind == TypeData::AggregateInst ) {
    760     // don't duplicate members
    761     if( newnode->type->aggInst->aggregate->kind == TypeData::Enum ) {
    762       delete newnode->type->aggInst->aggregate->enumeration->constants;
    763       newnode->type->aggInst->aggregate->enumeration->constants = 0;
    764     } else {
    765       assert( newnode->type->aggInst->aggregate->kind == TypeData::Aggregate );
    766       delete newnode->type->aggInst->aggregate->aggregate->members;
    767       newnode->type->aggInst->aggregate->aggregate->members = 0;
    768     }
    769   }
    770   newnode->type->forall = maybeClone( type->forall );
    771   newnode->storageClasses = storageClasses;
    772   newnode->name = assign_strptr( newName );
    773   return newnode;
    774 }
    775 
    776 DeclarationNode *
    777 DeclarationNode::cloneBaseType( DeclarationNode *o )
    778 {
    779   if( o ) {
    780     o->storageClasses.insert( o->storageClasses.end(), storageClasses.begin(), storageClasses.end() );
    781     if ( type ) {
    782       TypeData *srcType = type;
    783       while( srcType->base ) {
    784         srcType = srcType->base;
    785       }
    786       TypeData *newType = srcType->clone();
    787       if( newType->kind == TypeData::AggregateInst ) {
    788         // don't duplicate members
    789         if( newType->aggInst->aggregate->kind == TypeData::Enum ) {
    790           delete newType->aggInst->aggregate->enumeration->constants;
    791           newType->aggInst->aggregate->enumeration->constants = 0;
    792         } else {
    793           assert( newType->aggInst->aggregate->kind == TypeData::Aggregate );
    794           delete newType->aggInst->aggregate->aggregate->members;
    795           newType->aggInst->aggregate->aggregate->members = 0;
    796         }
    797       }
    798       newType->forall = maybeClone( type->forall );
    799       if( !o->type ) {
    800         o->type = newType;
    801       } else {
    802         addTypeToType( newType, o->type );
    803         delete newType;
    804       }
    805     }
    806   }
    807   return o;
    808 }
    809 
    810 DeclarationNode *
    811 DeclarationNode::cloneType( string *newName )
    812 {
    813   DeclarationNode *newnode = new DeclarationNode;
    814   newnode->type = maybeClone( type );
    815   newnode->storageClasses = storageClasses;
    816   newnode->name = assign_strptr( newName );
    817   return newnode;
    818 }
    819 
    820 DeclarationNode *
    821 DeclarationNode::cloneType( DeclarationNode *o )
    822 {
    823   if( o ) {
    824     o->storageClasses.insert( o->storageClasses.end(), storageClasses.begin(), storageClasses.end() );
    825     if ( type ) {
    826       TypeData *newType = type->clone();
    827       if( !o->type ) {
    828         o->type = newType;
    829       } else {
    830         addTypeToType( newType, o->type );
    831         delete newType;
    832       }
    833     }
    834   }
    835   return o;
    836 }
    837 
    838 DeclarationNode *
    839 DeclarationNode::appendList( DeclarationNode *node )
    840 {
    841   if( node != 0 ) {
    842     set_link( node );
    843   }
    844   return this;
    845 }
    846 
    847 DeclarationNode*
    848 DeclarationNode::extractAggregate() const
    849 {
    850   if( type ) {
    851     TypeData *ret = type->extractAggregate();
    852     if( ret ) {
    853       DeclarationNode *newnode = new DeclarationNode;
    854       newnode->type = ret;
    855       return newnode;
    856     } else {
    857       return 0;
    858     }
    859   } else {
    860     return 0;
    861   }
    862 }
    863 
    864 void buildList( const DeclarationNode *firstNode, std::list< Declaration* > &outputList )
    865 {
    866   SemanticError errors;
    867   std::back_insert_iterator< std::list< Declaration* > > out( outputList );
    868   const DeclarationNode *cur = firstNode;
    869   while( cur ) {
    870     try {
    871       if( DeclarationNode *extr = cur->extractAggregate() ) {
    872         // handle the case where a structure declaration is contained within an object or type
    873         // declaration
    874         Declaration *decl = extr->build();
    875         if( decl ) {
    876           *out++ = decl;
    877         }
    878       }
    879       Declaration *decl = cur->build();
    880       if( decl ) {
    881         *out++ = decl;
    882       }
    883     } catch( SemanticError &e ) {
    884       errors.append( e );
    885     }
    886     cur = dynamic_cast< DeclarationNode* >( cur->get_link() );
    887   }
    888   if( !errors.isEmpty() ) {
    889     throw errors;
    890   }
    891 }
    892 
    893 void buildList( const DeclarationNode *firstNode, std::list< DeclarationWithType* > &outputList )
    894 {
    895   SemanticError errors;
    896   std::back_insert_iterator< std::list< DeclarationWithType* > > out( outputList );
    897   const DeclarationNode *cur = firstNode;
    898   while( cur ) {
    899     try {
    900 ///       if( DeclarationNode *extr = cur->extractAggregate() ) {
     749        return 0;
     750    }
     751}
     752
     753void buildList( const DeclarationNode *firstNode, std::list< Declaration* > &outputList ) {
     754    SemanticError errors;
     755    std::back_insert_iterator< std::list< Declaration* > > out( outputList );
     756    const DeclarationNode *cur = firstNode;
     757    while( cur ) {
     758        try {
     759            if ( DeclarationNode *extr = cur->extractAggregate() ) {
     760                // handle the case where a structure declaration is contained within an object or type
     761                // declaration
     762                Declaration *decl = extr->build();
     763                if ( decl ) {
     764                   *out++ = decl;
     765                }
     766            }
     767            Declaration *decl = cur->build();
     768            if ( decl ) {
     769                *out++ = decl;
     770            }
     771        } catch( SemanticError &e ) {
     772            errors.append( e );
     773        }
     774        cur = dynamic_cast< DeclarationNode* >( cur->get_link() );
     775    }
     776    if ( ! errors.isEmpty() ) {
     777        throw errors;
     778    }
     779}
     780
     781void buildList( const DeclarationNode *firstNode, std::list< DeclarationWithType* > &outputList ) {
     782    SemanticError errors;
     783    std::back_insert_iterator< std::list< DeclarationWithType* > > out( outputList );
     784    const DeclarationNode *cur = firstNode;
     785    while( cur ) {
     786        try {
     787///       if ( DeclarationNode *extr = cur->extractAggregate() ) {
    901788///     // handle the case where a structure declaration is contained within an object or type
    902789///     // declaration
    903790///     Declaration *decl = extr->build();
    904 ///     if( decl ) {
    905 ///           *out++ = decl;
     791///     if ( decl ) {
     792///          *out++ = decl;
    906793///     }
    907794///       }
    908       Declaration *decl = cur->build();
    909       if( decl ) {
    910         if( DeclarationWithType *dwt = dynamic_cast< DeclarationWithType* >( decl ) ) {
    911           *out++ = dwt;
    912         } else if( StructDecl *agg = dynamic_cast< StructDecl* >( decl ) ) {
    913           StructInstType *inst = new StructInstType( Type::Qualifiers(), agg->get_name() );
    914           *out++ = new ObjectDecl( "", Declaration::NoStorageClass, linkage, 0, inst, 0 );
    915           delete agg;
    916         } else if( UnionDecl *agg = dynamic_cast< UnionDecl* >( decl ) ) {
    917           UnionInstType *inst = new UnionInstType( Type::Qualifiers(), agg->get_name() );
    918           *out++ = new ObjectDecl( "", Declaration::NoStorageClass, linkage, 0, inst, 0 );
    919         }
     795            Declaration *decl = cur->build();
     796            if ( decl ) {
     797                if ( DeclarationWithType *dwt = dynamic_cast< DeclarationWithType* >( decl ) ) {
     798                   *out++ = dwt;
     799                } else if ( StructDecl *agg = dynamic_cast< StructDecl* >( decl ) ) {
     800                    StructInstType *inst = new StructInstType( Type::Qualifiers(), agg->get_name() );
     801                   *out++ = new ObjectDecl( "", Declaration::NoStorageClass, linkage, 0, inst, 0 );
     802                    delete agg;
     803                } else if ( UnionDecl *agg = dynamic_cast< UnionDecl* >( decl ) ) {
     804                    UnionInstType *inst = new UnionInstType( Type::Qualifiers(), agg->get_name() );
     805                   *out++ = new ObjectDecl( "", Declaration::NoStorageClass, linkage, 0, inst, 0 );
     806                }
     807            }
     808        } catch( SemanticError &e ) {
     809            errors.append( e );
     810        }
     811        cur = dynamic_cast< DeclarationNode* >( cur->get_link() );
     812    }
     813    if ( ! errors.isEmpty() ) {
     814        throw errors;
     815    }
     816}
     817
     818void buildTypeList( const DeclarationNode *firstNode, std::list< Type* > &outputList ) {
     819    SemanticError errors;
     820    std::back_insert_iterator< std::list< Type* > > out( outputList );
     821    const DeclarationNode *cur = firstNode;
     822    while( cur ) {
     823        try {
     824           *out++ = cur->buildType();
     825        } catch( SemanticError &e ) {
     826            errors.append( e );
     827        }
     828        cur = dynamic_cast< DeclarationNode* >( cur->get_link() );
     829    }
     830    if ( ! errors.isEmpty() ) {
     831        throw errors;
     832    }
     833}
     834
     835Declaration *DeclarationNode::build() const {
     836
     837    if ( ! type ) {
     838        if ( buildInline() ) {
     839            throw SemanticError( "invalid inline specification in declaration of ", this );
     840        } else {
     841            return new ObjectDecl( name, buildStorageClass(), linkage, maybeBuild< Expression >( bitfieldWidth ), 0, maybeBuild< Initializer >( initializer ) );
     842        }
     843    } else {
     844        Declaration *newDecl = type->buildDecl( name, buildStorageClass(), maybeBuild< Expression >( bitfieldWidth ), buildInline(), linkage, maybeBuild< Initializer >(initializer) );
     845        return newDecl;
     846    }
     847    // we should never get here
     848    assert( false );
     849    return 0;
     850}
     851
     852Type *DeclarationNode::buildType() const {
     853    assert( type );
     854 
     855    switch ( type->kind ) {
     856      case TypeData::Enum:
     857        return new EnumInstType( type->buildQualifiers(), type->enumeration->name );
     858      case TypeData::Aggregate: {
     859          ReferenceToType *ret;
     860          switch ( type->aggregate->kind ) {
     861            case DeclarationNode::Struct:
     862              ret = new StructInstType( type->buildQualifiers(), type->aggregate->name );
     863              break;
     864
     865            case DeclarationNode::Union:
     866              ret = new UnionInstType( type->buildQualifiers(), type->aggregate->name );
     867              break;
     868
     869            case DeclarationNode::Context:
     870              ret = new ContextInstType( type->buildQualifiers(), type->aggregate->name );
     871              break;
     872
     873            default:
     874              assert( false );
     875          }
     876          buildList( type->aggregate->actuals, ret->get_parameters() );
     877          return ret;
    920878      }
    921     } catch( SemanticError &e ) {
    922       errors.append( e );
    923     }
    924     cur = dynamic_cast< DeclarationNode* >( cur->get_link() );
    925   }
    926   if( !errors.isEmpty() ) {
    927     throw errors;
    928   }
    929 }
    930 
    931 void buildTypeList( const DeclarationNode *firstNode, std::list< Type* > &outputList )
    932 {
    933   SemanticError errors;
    934   std::back_insert_iterator< std::list< Type* > > out( outputList );
    935   const DeclarationNode *cur = firstNode;
    936   while( cur ) {
    937     try {
    938       *out++ = cur->buildType();
    939     } catch( SemanticError &e ) {
    940       errors.append( e );
    941     }
    942     cur = dynamic_cast< DeclarationNode* >( cur->get_link() );
    943   }
    944   if( !errors.isEmpty() ) {
    945     throw errors;
    946   }
    947 }
    948 
    949 Declaration *
    950 DeclarationNode::build() const
    951 {
    952 
    953   if( !type ) {
    954     if( buildInline() ) {
    955       throw SemanticError( "invalid inline specification in declaration of ", this );
     879      case TypeData::Symbolic: {
     880          TypeInstType *ret = new TypeInstType( type->buildQualifiers(), type->symbolic->name, false );
     881          buildList( type->symbolic->actuals, ret->get_parameters() );
     882          return ret;
     883      }
     884      default:
     885        return type->build();
     886    }
     887}
     888
     889Declaration::StorageClass DeclarationNode::buildStorageClass() const {
     890    static const Declaration::StorageClass scMap[] = { 
     891        Declaration::Static,
     892        Declaration::Auto,
     893        Declaration::Extern,
     894        Declaration::Register,
     895        Declaration::NoStorageClass, // inline
     896        Declaration::Fortran
     897    }; 
     898 
     899    Declaration::StorageClass ret = Declaration::NoStorageClass;
     900    for ( std::list< StorageClass >::const_iterator i = storageClasses.begin(); i != storageClasses.end(); ++i ) {
     901        assert( unsigned( *i ) < sizeof( scMap ) / sizeof( scMap[0] ) );
     902        if ( *i == Inline ) continue;
     903        if ( ret == Declaration::NoStorageClass ) {
     904            ret = scMap[ *i ];
     905        } else {
     906            throw SemanticError( "invalid combination of storage classes in declaration of ", this );
     907        }
     908    }
     909    return ret;
     910}
     911
     912bool DeclarationNode::buildInline() const {
     913    std::list< StorageClass >::const_iterator first = std::find( storageClasses.begin(), storageClasses.end(), Inline );
     914    if ( first == storageClasses.end() ) {
     915        return false;
    956916    } else {
    957       return new ObjectDecl( name, buildStorageClass(), linkage, maybeBuild< Expression >( bitfieldWidth ), 0, maybeBuild< Initializer >( initializer ) );
    958     }
    959   } else {
    960     Declaration *newDecl = type->buildDecl( name, buildStorageClass(), maybeBuild< Expression >( bitfieldWidth ), buildInline(), linkage, maybeBuild< Initializer >(initializer) );
    961     return newDecl;
    962   }
    963   // we should never get here
    964   assert( false );
    965   return 0;
    966 }
    967 
    968 Type *
    969 DeclarationNode::buildType() const
    970 {
    971 
    972   assert( type );
    973  
    974   switch( type->kind ) {
    975   case TypeData::Enum:
    976     return new EnumInstType( type->buildQualifiers(), type->enumeration->name );
    977    
    978   case TypeData::Aggregate: {
    979     ReferenceToType *ret;
    980     switch( type->aggregate->kind ) {
    981     case DeclarationNode::Struct:
    982       ret = new StructInstType( type->buildQualifiers(), type->aggregate->name );
    983       break;
    984 
    985     case DeclarationNode::Union:
    986       ret = new UnionInstType( type->buildQualifiers(), type->aggregate->name );
    987       break;
    988 
    989     case DeclarationNode::Context:
    990       ret = new ContextInstType( type->buildQualifiers(), type->aggregate->name );
    991       break;
    992 
    993     default:
    994       assert( false );
    995     }
    996     buildList( type->aggregate->actuals, ret->get_parameters() );
    997     return ret;
    998   }
    999  
    1000   case TypeData::Symbolic: {
    1001     TypeInstType *ret = new TypeInstType( type->buildQualifiers(), type->symbolic->name, false );
    1002     buildList( type->symbolic->actuals, ret->get_parameters() );
    1003     return ret;
    1004   }
    1005  
    1006   default:
    1007     return type->build();
    1008   }
    1009 }
    1010 
    1011 Declaration::StorageClass
    1012 DeclarationNode::buildStorageClass() const
    1013 {
    1014   static const Declaration::StorageClass scMap[] = { 
    1015     Declaration::Static,
    1016     Declaration::Auto,
    1017     Declaration::Extern,
    1018     Declaration::Register,
    1019     Declaration::NoStorageClass, // inline
    1020     Declaration::Fortran
    1021   }; 
    1022  
    1023   Declaration::StorageClass ret = Declaration::NoStorageClass;
    1024   for( std::list< StorageClass >::const_iterator i = storageClasses.begin(); i != storageClasses.end(); ++i ) {
    1025     assert( unsigned( *i ) < sizeof( scMap ) / sizeof( scMap[0] ) );
    1026     if( *i == Inline ) continue;
    1027     if( ret == Declaration::NoStorageClass ) {
    1028       ret = scMap[ *i ];
    1029     } else {
    1030       throw SemanticError( "invalid combination of storage classes in declaration of ", this );
    1031     }
    1032   }
    1033   return ret;
    1034 }
    1035 
    1036 bool
    1037 DeclarationNode::buildInline() const
    1038 {
    1039   std::list< StorageClass >::const_iterator first = std::find( storageClasses.begin(), storageClasses.end(), Inline );
    1040   if( first == storageClasses.end() ) {
     917        std::list< StorageClass >::const_iterator next = std::find( ++first, storageClasses.end(), Inline );
     918        if ( next == storageClasses.end() ) {
     919            return true;
     920        } else {
     921            throw SemanticError( "duplicate inline specification in declaration of ", this );
     922        }
     923    }
     924    // we should never get here
    1041925    return false;
    1042   } else {
    1043     std::list< StorageClass >::const_iterator next = std::find( ++first, storageClasses.end(), Inline );
    1044     if( next == storageClasses.end() ) {
    1045       return true;
    1046     } else {
    1047       throw SemanticError( "duplicate inline specification in declaration of ", this );
    1048     }
    1049   }
    1050   // we should never get here
    1051   return false;
    1052 }
     926}
Note: See TracChangeset for help on using the changeset viewer.