Changeset 781
- Timestamp:
- 12/05/10 20:54:55 (14 years ago)
- Files:
-
- branches/dmd-1.x/src/class.c (modified) (1 diff)
- branches/dmd-1.x/src/declaration.c (modified) (2 diffs)
- branches/dmd-1.x/src/declaration.h (modified) (1 diff)
- branches/dmd-1.x/src/func.c (modified) (2 diffs)
- trunk/src/class.c (modified) (1 diff)
- trunk/src/declaration.c (modified) (2 diffs)
- trunk/src/declaration.h (modified) (1 diff)
- trunk/src/func.c (modified) (3 diffs)
- trunk/src/struct.c (modified) (1 diff)
Legend:
- Unmodified
- Added
- Removed
- Modified
- Copied
- Moved
branches/dmd-1.x/src/class.c
r650 r781 544 544 } 545 545 } 546 546 else 547 547 assert(0); 548 548 assert(!vthis); 549 549 vthis = new ThisDeclaration(loc, t); 550 550 members->push(vthis); 551 551 } 552 552 } 553 553 } 554 554 } 555 555 556 556 if (storage_class & STCauto) 557 557 error("storage class 'auto' is invalid when declaring a class, did you mean to use 'scope'?"); 558 558 if (storage_class & STCscope) 559 559 isscope = 1; 560 560 if (storage_class & STCabstract) 561 561 isabstract = 1; 562 562 563 563 sc = sc->push(this); 564 sc->stc &= ~(STCfinal | STCauto | STCscope | STCstatic | 565 STCabstract | STCdeprecated); 564 sc->stc &= STCsafe | STCtrusted | STCsystem; 566 565 sc->parent = this; 567 566 sc->inunion = 0; 568 567 569 568 if (isCOMclass()) 570 569 { 571 570 #if _WIN32 572 571 sc->linkage = LINKwindows; 573 572 #else 574 573 /* This enables us to use COM objects under Linux and 575 574 * work with things like XPCOM 576 575 */ 577 576 sc->linkage = LINKc; 578 577 #endif 579 578 } 580 579 sc->protection = PROTpublic; 581 580 sc->explicitProtection = 0; 582 581 sc->structalign = 8; 583 582 structalign = sc->structalign; 584 583 if (baseClass) 585 584 { sc->offset = baseClass->structsize; branches/dmd-1.x/src/declaration.c
r754 r781 728 728 else 729 729 sv->hinit = hinit->syntaxCopy(); 730 730 #endif 731 731 return sv; 732 732 } 733 733 734 734 void VarDeclaration::semantic(Scope *sc) 735 735 { 736 736 #if 0 737 737 printf("VarDeclaration::semantic('%s', parent = '%s')\n", toChars(), sc->parent->toChars()); 738 738 printf(" type = %s\n", type ? type->toChars() : "null"); 739 739 printf(" stc = x%x\n", sc->stc); 740 740 printf(" storage_class = x%x\n", storage_class); 741 741 printf("linkage = %d\n", sc->linkage); 742 742 //if (strcmp(toChars(), "mul") == 0) halt(); 743 743 #endif 744 744 745 745 storage_class |= sc->stc; 746 746 if (storage_class & STCextern && init) 747 747 error("extern symbols cannot have initializers"); 748 749 AggregateDeclaration *ad = isThis(); 750 if (ad) 751 storage_class |= ad->storage_class & STC_TYPECTOR; 748 752 749 753 /* If auto type inference, do the inference 750 754 */ 751 755 int inferred = 0; 752 756 if (!type) 753 757 { inuse++; 754 758 type = init->inferType(sc); 755 759 inuse--; 756 760 inferred = 1; 757 761 758 762 /* This is a kludge to support the existing syntax for RAII 759 763 * declarations. 760 764 */ 761 765 storage_class &= ~STCauto; 762 766 originalType = type; 763 767 } 764 768 else 765 769 { if (!originalType) 766 770 originalType = type; 767 771 type = type->semantic(loc, sc); … … 1277 1281 * too. 1278 1282 */ 1279 1283 if (type) 1280 1284 type->toCBuffer(buf, ident, hgs); 1281 1285 else 1282 1286 buf->writestring(ident->toChars()); 1283 1287 if (init) 1284 1288 { buf->writestring(" = "); 1285 1289 #if DMDV2 1286 1290 ExpInitializer *ie = init->isExpInitializer(); 1287 1291 if (ie && (ie->exp->op == TOKconstruct || ie->exp->op == TOKblit)) 1288 1292 ((AssignExp *)ie->exp)->e2->toCBuffer(buf, hgs); 1289 1293 else 1290 1294 #endif 1291 1295 init->toCBuffer(buf, hgs); 1292 1296 } 1293 1297 buf->writeByte(';'); 1294 1298 buf->writenl(); 1295 1299 } 1296 1300 1301 AggregateDeclaration *VarDeclaration::isThis() 1302 { 1303 AggregateDeclaration *ad = NULL; 1304 1305 if (!(storage_class & (STCstatic | STCextern | STCmanifest | STCtemplateparameter | 1306 STCtls | STCgshared | STCctfe))) 1307 { 1308 if ((storage_class & (STCconst | STCimmutable)) && init) 1309 return NULL; 1310 1311 for (Dsymbol *s = this; s; s = s->parent) 1312 { 1313 ad = s->isMember(); 1314 if (ad) 1315 break; 1316 if (!s->parent || !s->parent->isTemplateMixin()) break; 1317 } 1318 } 1319 return ad; 1320 } 1321 1297 1322 int VarDeclaration::needThis() 1298 1323 { 1299 1324 //printf("VarDeclaration::needThis(%s, x%x)\n", toChars(), storage_class); 1300 1325 return storage_class & STCfield; 1301 1326 } 1302 1327 1303 1328 int VarDeclaration::isImportedSymbol() 1304 1329 { 1305 1330 if (protection == PROTexport && !init && (isStatic() || isConst() || parent->isModule())) 1306 1331 return TRUE; 1307 1332 return FALSE; 1308 1333 } 1309 1334 1310 1335 void VarDeclaration::checkCtorConstInit() 1311 1336 { 1312 1337 if (ctorinit == 0 && isCtorinit() && !(storage_class & STCfield)) 1313 1338 error("missing initializer in static constructor for const variable"); 1314 1339 } 1315 1340 1316 1341 /************************************ branches/dmd-1.x/src/declaration.h
r719 r781 258 258 int canassign; // it can be assigned to 259 259 Dsymbol *aliassym; // if redone as alias to another symbol 260 260 Expression *value; // when interpreting, this is the value 261 261 // (NULL if value not determinable) 262 262 #if DMDV2 263 263 VarDeclaration *rundtor; // if !NULL, rundtor is tested at runtime to see 264 264 // if the destructor should be run. Used to prevent 265 265 // dtor calls on postblitted vars 266 266 #endif 267 267 268 268 VarDeclaration(Loc loc, Type *t, Identifier *id, Initializer *init); 269 269 Dsymbol *syntaxCopy(Dsymbol *); 270 270 void semantic(Scope *sc); 271 271 void semantic2(Scope *sc); 272 272 const char *kind(); 273 273 void toCBuffer(OutBuffer *buf, HdrGenState *hgs); 274 274 #ifdef _DH 275 275 Type *htype; 276 276 Initializer *hinit; 277 277 #endif 278 AggregateDeclaration *isThis(); 278 279 int needThis(); 279 280 int isImportedSymbol(); 280 281 int isDataseg(); 281 282 int isThreadlocal(); 282 283 int isCTFE(); 283 284 int hasPointers(); 284 285 #if DMDV2 285 286 int canTakeAddressOf(); 286 287 int needsAutoDtor(); 287 288 #endif 288 289 Expression *callScopeDtor(Scope *sc); 289 290 ExpInitializer *getExpInitializer(); 290 291 Expression *getConstInitializer(); 291 292 void checkCtorConstInit(); 292 293 void checkNestedReference(Scope *sc, Loc loc); 293 294 Dsymbol *toAlias(); 294 295 295 296 Symbol *toSymbol(); 296 297 void toObjFile(int multiobj); // compile to .obj file 297 298 int cvMember(unsigned char *p); branches/dmd-1.x/src/func.c
r738 r781 92 92 FuncDeclaration *f; 93 93 94 94 //printf("FuncDeclaration::syntaxCopy('%s')\n", toChars()); 95 95 if (s) 96 96 f = (FuncDeclaration *)s; 97 97 else 98 98 f = new FuncDeclaration(loc, endloc, ident, storage_class, type->syntaxCopy()); 99 99 f->outId = outId; 100 100 f->frequire = frequire ? frequire->syntaxCopy() : NULL; 101 101 f->fensure = fensure ? fensure->syntaxCopy() : NULL; 102 102 f->fbody = fbody ? fbody->syntaxCopy() : NULL; 103 103 assert(!fthrows); // deprecated 104 104 return f; 105 105 } 106 106 107 107 108 108 // Do the semantic analysis on the external interface to the function. 109 109 110 110 void FuncDeclaration::semantic(Scope *sc) 111 111 { TypeFunction *f; 112 AggregateDeclaration *ad; 112 113 StructDeclaration *sd; 113 114 ClassDeclaration *cd; 114 115 InterfaceDeclaration *id; 115 116 Dsymbol *pd; 116 117 117 118 #if 0 118 119 printf("FuncDeclaration::semantic(sc = %p, this = %p, '%s', linkage = %d)\n", sc, this, toPrettyChars(), sc->linkage); 119 120 if (isFuncLiteralDeclaration()) 120 121 printf("\tFuncLiteralDeclaration()\n"); 121 122 printf("sc->parent = %s, parent = %s\n", sc->parent->toChars(), parent ? parent->toChars() : ""); 122 123 printf("type: %p, %s\n", type, type->toChars()); 123 124 #endif 124 125 125 126 if (semanticRun != PASSinit && isFuncLiteralDeclaration()) 126 127 { 127 128 /* Member functions that have return types that are 128 129 * forward references can have semantic() run more than 129 130 * once on them. 130 131 * See test\interface2.d, test20 131 132 */ … … 151 153 foverrides.setDim(0); // reset in case semantic() is being retried for this function 152 154 153 155 if (!originalType) 154 156 originalType = type; 155 157 if (!type->deco) 156 158 { 157 159 type = type->semantic(loc, sc); 158 160 } 159 161 //type->print(); 160 162 if (type->ty != Tfunction) 161 163 { 162 164 error("%s must be a function", toChars()); 163 165 return; 164 166 } 165 167 f = (TypeFunction *)(type); 166 168 size_t nparams = Parameter::dim(f->parameters); 167 169 168 170 linkage = sc->linkage; 169 171 protection = sc->protection; 170 172 storage_class |= sc->stc; 173 ad = isThis(); 174 if (ad) 175 storage_class |= ad->storage_class & (STC_TYPECTOR | STCsynchronized); 171 176 //printf("function storage_class = x%x\n", storage_class); 172 177 173 178 if (ident == Id::ctor && !isCtorDeclaration()) 174 179 error("_ctor is reserved for constructors"); 175 180 176 181 if (isConst() || isAuto() || isScope()) 177 182 error("functions cannot be const or auto"); 178 183 179 184 if (isAbstract() && !isVirtual()) 180 185 error("non-virtual functions cannot be abstract"); 181 186 182 187 if (isAbstract() && isFinal()) 183 188 error("cannot be both final and abstract"); 184 189 #if 0 185 190 if (isAbstract() && fbody) 186 191 error("abstract functions cannot have bodies"); 187 192 #endif 188 193 189 194 #if 0 190 195 if (isStaticConstructor() || isStaticDestructor()) 191 196 { 192 197 if (!isStatic() || type->nextOf()->ty != Tvoid) 193 198 error("static constructors / destructors must be static void"); 194 199 if (f->arguments && f->arguments->dim) 195 200 error("static constructors / destructors must have empty parameter list"); 196 201 // BUG: check for invalid storage classes 197 202 } 198 203 #endif 199 204 200 205 #ifdef IN_GCC 201 AggregateDeclaration *ad;202 203 ad = parent->isAggregateDeclaration();204 if (ad)205 ad->methods.push(this);206 { 207 AggregateDeclaration *ad = parent->isAggregateDeclaration(); 208 if (ad) 209 ad->methods.push(this); 210 } 206 211 #endif 207 212 sd = parent->isStructDeclaration(); 208 213 if (sd) 209 214 { 210 215 // Verify no constructors, destructors, etc. 211 216 if (isCtorDeclaration() || 212 217 isDtorDeclaration() 213 218 //|| isInvariantDeclaration() 214 219 //|| isUnitTestDeclaration() 215 220 ) 216 221 { 217 222 error("special member functions not allowed for %ss", sd->kind()); 218 223 } 219 224 220 225 #if 0 221 226 if (!sd->inv) 222 227 sd->inv = isInvariantDeclaration(); 223 228 224 229 if (!sd->aggNew) 225 230 sd->aggNew = isNewDeclaration(); trunk/src/class.c
r776 r781 561 561 } 562 562 } 563 563 } 564 564 } 565 565 566 566 if (storage_class & STCauto) 567 567 error("storage class 'auto' is invalid when declaring a class, did you mean to use 'scope'?"); 568 568 if (storage_class & STCscope) 569 569 isscope = 1; 570 570 if (storage_class & STCabstract) 571 571 isabstract = 1; 572 572 573 573 if (storage_class & STCimmutable) 574 574 type = type->addMod(MODimmutable); 575 575 if (storage_class & STCconst) 576 576 type = type->addMod(MODconst); 577 577 if (storage_class & STCshared) 578 578 type = type->addMod(MODshared); 579 579 580 580 sc = sc->push(this); 581 sc->stc &= ~(STCfinal | STCauto | STCscope | STCstatic |582 STCabstract | STCdeprecated | STC_TYPECTOR | STCtls | STCgshared);583 sc->stc |= storage_class & STC_TYPECTOR;581 //sc->stc &= ~(STCfinal | STCauto | STCscope | STCstatic | STCabstract | STCdeprecated | STC_TYPECTOR | STCtls | STCgshared); 582 //sc->stc |= storage_class & STC_TYPECTOR; 583 sc->stc &= STCsafe | STCtrusted | STCsystem; 584 584 sc->parent = this; 585 585 sc->inunion = 0; 586 586 587 587 if (isCOMclass()) 588 588 { 589 589 #if _WIN32 590 590 sc->linkage = LINKwindows; 591 591 #else 592 592 /* This enables us to use COM objects under Linux and 593 593 * work with things like XPCOM 594 594 */ 595 595 sc->linkage = LINKc; 596 596 #endif 597 597 } 598 598 sc->protection = PROTpublic; 599 599 sc->explicitProtection = 0; 600 600 sc->structalign = 8; 601 601 structalign = sc->structalign; 602 602 if (baseClass) 603 603 { sc->offset = baseClass->structsize; trunk/src/declaration.c
r780 r781 718 718 printf(" stc = x%x\n", sc->stc); 719 719 printf(" storage_class = x%x\n", storage_class); 720 720 printf("linkage = %d\n", sc->linkage); 721 721 //if (strcmp(toChars(), "mul") == 0) halt(); 722 722 #endif 723 723 724 724 // if (sem > SemanticStart) 725 725 // return; 726 726 // sem = SemanticIn; 727 727 728 728 if (scope) 729 729 { sc = scope; 730 730 scope = NULL; 731 731 } 732 732 733 733 /* Pick up storage classes from context, but skip synchronized 734 734 */ 735 735 storage_class |= (sc->stc & ~STCsynchronized); 736 736 if (storage_class & STCextern && init) 737 737 error("extern symbols cannot have initializers"); 738 739 AggregateDeclaration *ad = isThis(); 740 if (ad) 741 storage_class |= ad->storage_class & STC_TYPECTOR; 738 742 739 743 /* If auto type inference, do the inference 740 744 */ 741 745 int inferred = 0; 742 746 if (!type) 743 747 { inuse++; 744 748 745 749 ArrayInitializer *ai = init->isArrayInitializer(); 746 750 if (ai) 747 751 { Expression *e; 748 752 if (ai->isAssociativeArray()) 749 753 e = ai->toAssocArrayLiteral(); 750 754 else 751 755 e = init->toExpression(); 752 756 if (!e) 753 757 { 754 758 error("cannot infer type from initializer"); 755 759 e = new ErrorExp(); 756 760 } 757 761 init = new ExpInitializer(e->loc, e); … … 1378 1382 * too. 1379 1383 */ 1380 1384 if (type) 1381 1385 type->toCBuffer(buf, ident, hgs); 1382 1386 else 1383 1387 buf->writestring(ident->toChars()); 1384 1388 if (init) 1385 1389 { buf->writestring(" = "); 1386 1390 #if DMDV2 1387 1391 ExpInitializer *ie = init->isExpInitializer(); 1388 1392 if (ie && (ie->exp->op == TOKconstruct || ie->exp->op == TOKblit)) 1389 1393 ((AssignExp *)ie->exp)->e2->toCBuffer(buf, hgs); 1390 1394 else 1391 1395 #endif 1392 1396 init->toCBuffer(buf, hgs); 1393 1397 } 1394 1398 buf->writeByte(';'); 1395 1399 buf->writenl(); 1396 1400 } 1397 1401 1402 AggregateDeclaration *VarDeclaration::isThis() 1403 { 1404 AggregateDeclaration *ad = NULL; 1405 1406 if (!(storage_class & (STCstatic | STCextern | STCmanifest | STCtemplateparameter | 1407 STCtls | STCgshared | STCctfe))) 1408 { 1409 if ((storage_class & (STCconst | STCimmutable | STCwild)) && init) 1410 return NULL; 1411 1412 for (Dsymbol *s = this; s; s = s->parent) 1413 { 1414 ad = s->isMember(); 1415 if (ad) 1416 break; 1417 if (!s->parent || !s->parent->isTemplateMixin()) break; 1418 } 1419 } 1420 return ad; 1421 } 1422 1398 1423 int VarDeclaration::needThis() 1399 1424 { 1400 1425 //printf("VarDeclaration::needThis(%s, x%x)\n", toChars(), storage_class); 1401 1426 return storage_class & STCfield; 1402 1427 } 1403 1428 1404 1429 int VarDeclaration::isImportedSymbol() 1405 1430 { 1406 1431 if (protection == PROTexport && !init && 1407 1432 (storage_class & STCstatic || parent->isModule())) 1408 1433 return TRUE; 1409 1434 return FALSE; 1410 1435 } 1411 1436 1412 1437 void VarDeclaration::checkCtorConstInit() 1413 1438 { 1414 1439 #if 0 /* doesn't work if more than one static ctor */ 1415 1440 if (ctorinit == 0 && isCtorinit() && !(storage_class & STCfield)) 1416 1441 error("missing initializer in static constructor for const variable"); 1417 1442 #endif trunk/src/declaration.h
r756 r781 253 253 int canassign; // it can be assigned to 254 254 Dsymbol *aliassym; // if redone as alias to another symbol 255 255 Expression *value; // when interpreting, this is the value 256 256 // (NULL if value not determinable) 257 257 #if DMDV2 258 258 VarDeclaration *rundtor; // if !NULL, rundtor is tested at runtime to see 259 259 // if the destructor should be run. Used to prevent 260 260 // dtor calls on postblitted vars 261 261 #endif 262 262 263 263 VarDeclaration(Loc loc, Type *t, Identifier *id, Initializer *init); 264 264 Dsymbol *syntaxCopy(Dsymbol *); 265 265 void semantic(Scope *sc); 266 266 void semantic2(Scope *sc); 267 267 const char *kind(); 268 268 void toCBuffer(OutBuffer *buf, HdrGenState *hgs); 269 269 #ifdef _DH 270 270 Type *htype; 271 271 Initializer *hinit; 272 272 #endif 273 AggregateDeclaration *isThis(); 273 274 int needThis(); 274 275 int isImportedSymbol(); 275 276 int isDataseg(); 276 277 int isThreadlocal(); 277 278 int isCTFE(); 278 279 int hasPointers(); 279 280 #if DMDV2 280 281 int canTakeAddressOf(); 281 282 int needsAutoDtor(); 282 283 #endif 283 284 Expression *callScopeDtor(Scope *sc); 284 285 ExpInitializer *getExpInitializer(); 285 286 Expression *getConstInitializer(); 286 287 void checkCtorConstInit(); 287 288 void checkNestedReference(Scope *sc, Loc loc); 288 289 Dsymbol *toAlias(); 289 290 290 291 Symbol *toSymbol(); 291 292 void toObjFile(int multiobj); // compile to .obj file 292 293 int cvMember(unsigned char *p); trunk/src/func.c
r756 r781 92 92 FuncDeclaration *f; 93 93 94 94 //printf("FuncDeclaration::syntaxCopy('%s')\n", toChars()); 95 95 if (s) 96 96 f = (FuncDeclaration *)s; 97 97 else 98 98 f = new FuncDeclaration(loc, endloc, ident, storage_class, type->syntaxCopy()); 99 99 f->outId = outId; 100 100 f->frequire = frequire ? frequire->syntaxCopy() : NULL; 101 101 f->fensure = fensure ? fensure->syntaxCopy() : NULL; 102 102 f->fbody = fbody ? fbody->syntaxCopy() : NULL; 103 103 assert(!fthrows); // deprecated 104 104 return f; 105 105 } 106 106 107 107 108 108 // Do the semantic analysis on the external interface to the function. 109 109 110 110 void FuncDeclaration::semantic(Scope *sc) 111 111 { TypeFunction *f; 112 AggregateDeclaration *ad; 112 113 StructDeclaration *sd; 113 114 ClassDeclaration *cd; 114 115 InterfaceDeclaration *id; 115 116 Dsymbol *pd; 116 117 117 118 #if 0 118 119 printf("FuncDeclaration::semantic(sc = %p, this = %p, '%s', linkage = %d)\n", sc, this, toPrettyChars(), sc->linkage); 119 120 if (isFuncLiteralDeclaration()) 120 121 printf("\tFuncLiteralDeclaration()\n"); 121 122 printf("sc->parent = %s, parent = %s\n", sc->parent->toChars(), parent ? parent->toChars() : ""); 122 123 printf("type: %p, %s\n", type, type->toChars()); 123 124 #endif 124 125 125 126 if (semanticRun != PASSinit && isFuncLiteralDeclaration()) 126 127 { 127 128 /* Member functions that have return types that are 128 129 * forward references can have semantic() run more than 129 130 * once on them. 130 131 * See test\interface2.d, test20 131 132 */ … … 137 138 138 139 if (semanticRun >= PASSsemanticdone) 139 140 { 140 141 if (!parent->isClassDeclaration()) 141 142 { 142 143 return; 143 144 } 144 145 // need to re-run semantic() in order to set the class's vtbl[] 145 146 } 146 147 else 147 148 { 148 149 assert(semanticRun <= PASSsemantic); 149 150 semanticRun = PASSsemantic; 150 151 } 151 152 152 153 unsigned dprogress_save = Module::dprogress; 153 154 154 155 foverrides.setDim(0); // reset in case semantic() is being retried for this function 155 156 156 157 storage_class |= sc->stc & ~STCref; 158 ad = isThis(); 159 if (ad) 160 storage_class |= ad->storage_class & (STC_TYPECTOR | STCsynchronized); 161 157 162 //printf("function storage_class = x%llx, sc->stc = x%llx, %x\n", storage_class, sc->stc, Declaration::isFinal()); 158 163 159 164 if (!originalType) 160 165 originalType = type; 161 166 if (!type->deco) 162 167 { 163 168 sc = sc->push(); 164 169 sc->stc |= storage_class & (STCref | STCnothrow | STCpure | STCdisable 165 170 | STCsafe | STCtrusted | STCsystem); // forward to function type 166 171 167 172 if (isCtorDeclaration()) 168 173 sc->flags |= SCOPEctor; 169 174 type = type->semantic(loc, sc); 170 175 sc = sc->pop(); 171 176 172 177 /* Apply const, immutable and shared storage class 173 178 * to the function type 174 179 */ 175 180 StorageClass stc = storage_class; 176 181 if (type->isImmutable()) … … 254 259 255 260 if (isAbstract() && isFinal()) 256 261 error("cannot be both final and abstract"); 257 262 #if 0 258 263 if (isAbstract() && fbody) 259 264 error("abstract functions cannot have bodies"); 260 265 #endif 261 266 262 267 #if 0 263 268 if (isStaticConstructor() || isStaticDestructor()) 264 269 { 265 270 if (!isStatic() || type->nextOf()->ty != Tvoid) 266 271 error("static constructors / destructors must be static void"); 267 272 if (f->arguments && f->arguments->dim) 268 273 error("static constructors / destructors must have empty parameter list"); 269 274 // BUG: check for invalid storage classes 270 275 } 271 276 #endif 272 277 273 278 #ifdef IN_GCC 274 AggregateDeclaration *ad;275 276 ad = parent->isAggregateDeclaration();277 if (ad)278 ad->methods.push(this);279 { 280 AggregateDeclaration *ad = parent->isAggregateDeclaration(); 281 if (ad) 282 ad->methods.push(this); 283 } 279 284 #endif 280 285 sd = parent->isStructDeclaration(); 281 286 if (sd) 282 287 { 283 288 if (isCtorDeclaration()) 284 289 { 285 290 goto Ldone; 286 291 } 287 292 #if 0 288 293 // Verify no constructors, destructors, etc. 289 294 if (isCtorDeclaration() 290 295 //||isDtorDeclaration() 291 296 //|| isInvariantDeclaration() 292 297 //|| isUnitTestDeclaration() 293 298 ) 294 299 { 295 300 error("special member functions not allowed for %ss", sd->kind()); 296 301 } 297 302 298 303 if (!sd->inv) trunk/src/struct.c
r776 r781 355 355 if (ad) 356 356 t = ad->handle; 357 357 else 358 358 t = Type::tvoidptr; 359 359 } 360 360 else 361 361 assert(0); 362 362 if (t->ty == Tstruct) 363 363 t = Type::tvoidptr; // t should not be a ref type 364 364 assert(!vthis); 365 365 vthis = new ThisDeclaration(loc, t); 366 366 //vthis->storage_class |= STCref; 367 367 members->push(vthis); 368 368 } 369 369 } 370 370 } 371 371 } 372 372 373 373 sizeok = 0; 374 374 sc2 = sc->push(this); 375 sc2->stc &= storage_class & STC_TYPECTOR;375 sc2->stc &= STCsafe | STCtrusted | STCsystem; 376 376 sc2->parent = this; 377 377 if (isUnionDeclaration()) 378 378 sc2->inunion = 1; 379 379 sc2->protection = PROTpublic; 380 380 sc2->explicitProtection = 0; 381 381 382 382 int members_dim = members->dim; 383 383 384 384 /* Set scope so if there are forward references, we still might be able to 385 385 * resolve individual members like enums. 386 386 */ 387 387 for (int i = 0; i < members_dim; i++) 388 388 { Dsymbol *s = (Dsymbol *)members->data[i]; 389 389 /* There are problems doing this in the general case because 390 390 * Scope keeps track of things like 'offset' 391 391 */ 392 392 if (s->isEnumDeclaration() || (s->isAggregateDeclaration() && s->ident)) 393 393 { 394 394 //printf("setScope %s %s\n", s->kind(), s->toChars()); 395 395 s->setScope(sc2);
