comparison dmd/FuncDeclaration.d @ 79:43073c7c7769

updated to 2.035 also implemented a few missing functions still crashes in Import.importAll though
author Trass3r
date Mon, 30 Aug 2010 03:57:51 +0200
parents ad4792a1cfd6
children be2ab491772e b17640f0e4e8
comparison
equal deleted inserted replaced
78:b98fa8a4bf04 79:43073c7c7769
276 StructDeclaration sd; 276 StructDeclaration sd;
277 ClassDeclaration cd; 277 ClassDeclaration cd;
278 InterfaceDeclaration id; 278 InterfaceDeclaration id;
279 Dsymbol pd; 279 Dsymbol pd;
280 280
281 static if (false) { 281 static if (false)
282 {
282 printf("FuncDeclaration.semantic(sc = %p, this = %p, '%s', linkage = %d)\n", sc, this, toPrettyChars(), sc.linkage); 283 printf("FuncDeclaration.semantic(sc = %p, this = %p, '%s', linkage = %d)\n", sc, this, toPrettyChars(), sc.linkage);
283 if (isFuncLiteralDeclaration()) 284 if (isFuncLiteralDeclaration())
284 printf("\tFuncLiteralDeclaration()\n"); 285 printf("\tFuncLiteralDeclaration()\n");
285 printf("sc.parent = %s, parent = %s\n", sc.parent.toChars(), parent ? parent.toChars() : ""); 286 printf("sc.parent = %s, parent = %s\n", sc.parent.toChars(), parent ? parent.toChars() : "");
286 printf("type: %p, %s\n", type, type.toChars()); 287 printf("type: %p, %s\n", type, type.toChars());
287 } 288 }
288 289
289 if (semanticRun && isFuncLiteralDeclaration()) 290 if (semanticRun && isFuncLiteralDeclaration())
290 { 291 {
291 /* Member functions that have return types that are 292 /* Member functions that have return types that are
292 * forward references can have semantic() run more than 293 * forward references can have semantic() run more than
293 * once on them. 294 * once on them.
294 * See test\interface2.d, test20 295 * See test\interface2.d, test20
295 */ 296 */
296 return; 297 return;
297 } 298 }
298 assert(semanticRun <= 1); 299 assert(semanticRun <= 1);
299 semanticRun = 1; 300 semanticRun = 1;
300 301
301 storage_class |= sc.stc & ~STC.STCref; 302 storage_class |= sc.stc & ~STC.STCref;
302 //printf("function storage_class = x%x\n", storage_class); 303 //printf("function storage_class = x%x\n", storage_class);
303 304
304 if (!originalType) 305 if (!originalType)
305 originalType = type; 306 originalType = type;
306 if (!type.deco) 307 if (!type.deco)
307 { 308 {
308 /* Apply const and invariant storage class 309 /* Apply const and invariant storage class
309 * to the function type 310 * to the function type
310 */ 311 */
311 type = type.semantic(loc, sc); 312 type = type.semantic(loc, sc);
312 STC stc = storage_class; 313 STC stc = storage_class;
313 if (type.isInvariant()) 314 if (type.isInvariant())
314 stc |= STC.STCimmutable; 315 stc |= STC.STCimmutable;
315 if (type.isConst()) 316 if (type.isConst())
316 stc |= STC.STCconst; 317 stc |= STC.STCconst;
317 if (type.isShared() || storage_class & STC.STCsynchronized) 318 if (type.isShared() || storage_class & STC.STCsynchronized)
318 stc |= STC.STCshared; 319 stc |= STC.STCshared;
319 switch (stc & STC.STC_TYPECTOR) 320 switch (stc & STC.STC_TYPECTOR)
320 { 321 {
321 case STC.STCimmutable: 322 case STC.STCimmutable:
322 case STC.STCimmutable | STC.STCconst: 323 case STC.STCimmutable | STC.STCconst:
323 case STC.STCimmutable | STC.STCconst | STC.STCshared: 324 case STC.STCimmutable | STC.STCconst | STC.STCshared:
324 case STC.STCimmutable | STC.STCshared: 325 case STC.STCimmutable | STC.STCshared:
325 // Don't use toInvariant(), as that will do a merge() 326 // Don't use toInvariant(), as that will do a merge()
326 type = type.makeInvariant(); 327 type = type.makeInvariant();
327 type.deco = type.merge().deco; 328 goto Lmerge;
328 break; 329
329 330 case STC.STCconst:
330 case STC.STCconst: 331 type = type.makeConst();
331 type = type.makeConst(); 332 goto Lmerge;
332 type.deco = type.merge().deco; 333
333 break; 334 case STC.STCshared | STC.STCconst:
334 335 type = type.makeSharedConst();
335 case STC.STCshared | STC.STCconst: 336 goto Lmerge;
336 type = type.makeSharedConst(); 337
337 type.deco = type.merge().deco; 338 case STC.STCshared:
338 break; 339 type = type.makeShared();
339 340 Lmerge:
340 case STC.STCshared: 341 if (!(type.ty == Tfunction && !type.nextOf()))
341 type = type.makeShared(); 342 /* Can't do merge if return type is not known yet
342 type.deco = type.merge().deco; 343 */
343 break; 344 type.deco = type.merge().deco;
344 345 break;
345 case STC.STCundefined: 346
346 break; 347 case STC.STCundefined:
347 348 break;
348 default: 349
349 assert(0); 350 default:
350 } 351 assert(0);
352 }
351 } 353 }
352 //type.print(); 354 //type.print();
353 if (type.ty != TY.Tfunction) 355 if (type.ty != TY.Tfunction)
354 { 356 {
355 error("%s must be a function", toChars()); 357 error("%s must be a function", toChars());
740 742
741 default: 743 default:
742 goto Lmainerr; 744 goto Lmainerr;
743 } 745 }
744 746
745 if (f.nextOf().ty != TY.Tint32 && f.nextOf().ty != TY.Tvoid) 747 if (!f.nextOf())
748 error("must return int or void");
749 else if (f.nextOf().ty != TY.Tint32 && f.nextOf().ty != TY.Tvoid)
746 error("must return int or void, not %s", f.nextOf().toChars()); 750 error("must return int or void, not %s", f.nextOf().toChars());
747 if (f.varargs) 751 if (f.varargs)
748 { 752 {
749 Lmainerr: 753 Lmainerr:
750 error("parameters must be main() or main(char[][] args)"); 754 error("parameters must be main() or main(char[][] args)");
1153 frequire = frequire.semantic(sc2); 1157 frequire = frequire.semantic(sc2);
1154 labtab = null; // so body can't refer to labels 1158 labtab = null; // so body can't refer to labels
1155 } 1159 }
1156 1160
1157 if (fensure || addPostInvariant()) 1161 if (fensure || addPostInvariant())
1158 { /* fensure is composed of the [out] contracts 1162 {
1163 /* fensure is composed of the [out] contracts
1159 */ 1164 */
1165 if (!type.nextOf()) // if return type is inferred
1166 {
1167 /* This case:
1168 * auto fp = function() out { } body { };
1169 * Can fix by doing semantic() onf fbody first.
1170 */
1171 error("post conditions are not supported if the return type is inferred");
1172 return;
1173 }
1174
1160 ScopeDsymbol sym = new ScopeDsymbol(); 1175 ScopeDsymbol sym = new ScopeDsymbol();
1161 sym.parent = sc2.scopesym; 1176 sym.parent = sc2.scopesym;
1162 sc2 = sc2.push(sym); 1177 sc2 = sc2.push(sym);
1163 1178
1164 assert(type.nextOf()); 1179 assert(type.nextOf());
1273 1288
1274 /* If this is a class constructor 1289 /* If this is a class constructor
1275 */ 1290 */
1276 if (isCtorDeclaration() && cd) 1291 if (isCtorDeclaration() && cd)
1277 { 1292 {
1278 for (int i = 0; i < cd.fields.dim; i++) 1293 for (int i = 0; i < cd.fields.dim; i++)
1279 { VarDeclaration v = cast(VarDeclaration)cd.fields.data[i]; 1294 { VarDeclaration v = cast(VarDeclaration)cd.fields[i];
1280 1295
1281 v.ctorinit = 0; 1296 v.ctorinit = 0;
1282 } 1297 }
1283 } 1298 }
1284 1299
1285 if (inferRetType || f.retStyle() != RET.RETstack) 1300 if (inferRetType || f.retStyle() != RET.RETstack)
1286 nrvo_can = 0; 1301 nrvo_can = 0;
1287 1302
1326 1341
1327 // Verify that all the ctorinit fields got initialized 1342 // Verify that all the ctorinit fields got initialized
1328 if (!(sc2.callSuper & CSX.CSXthis_ctor)) 1343 if (!(sc2.callSuper & CSX.CSXthis_ctor))
1329 { 1344 {
1330 for (int i = 0; i < cd.fields.dim; i++) 1345 for (int i = 0; i < cd.fields.dim; i++)
1331 { VarDeclaration v = cast(VarDeclaration)cd.fields.data[i]; 1346 { VarDeclaration v = cast(VarDeclaration)cd.fields[i];
1332 1347
1333 if (v.ctorinit == 0 && v.isCtorinit()) 1348 if (v.ctorinit == 0 && v.isCtorinit())
1334 error("missing initializer for final field %s", v.toChars()); 1349 error("missing initializer for final field %s", v.toChars());
1335 } 1350 }
1336 } 1351 }