1: 
   2: // Compiler implementation of the D programming language
   3: // Copyright (c) 1999-2011 by Digital Mars
   4: // All Rights Reserved
   5: // written by Walter Bright
   6: // http://www.digitalmars.com
   7: 
   8: #include <stdio.h>
   9: #include <stddef.h>
  10: #include <time.h>
  11: static char __file__[] = __FILE__;      /* for tassert.h                */
  12: #include        "tassert.h"
  13: 
  14: #if __sun&&__SVR4
  15: #include <alloca.h>
  16: #endif
  17: 
  18: #include "mars.h"
  19: #include "module.h"
  20: #include "mtype.h"
  21: #include "declaration.h"
  22: #include "statement.h"
  23: #include "enum.h"
  24: #include "aggregate.h"
  25: #include "init.h"
  26: #include "attrib.h"
  27: #include "id.h"
  28: #include "import.h"
  29: #include "template.h"
  30: #include "lib.h"
  31: 
  32: #include "rmem.h"
  33: #include "cc.h"
  34: #include "global.h"
  35: #include "oper.h"
  36: #include "code.h"
  37: #include "type.h"
  38: #include "dt.h"
  39: #include "cgcv.h"
  40: #include "outbuf.h"
  41: #include "irstate.h"
  42: 
  43: struct Environment;
  44: 
  45: Environment *benv;
  46: 
  47: void out_config_init();
  48: void slist_add(Symbol *s);
  49: void slist_reset();
  50: void clearStringTab();
  51: 
  52: #define STATICCTOR      0
  53: 
  54: elem *eictor;
  55: symbol *ictorlocalgot;
  56: elem *ector;
  57: StaticDtorDeclarations ectorgates;
  58: elem *edtor;
  59: elem *etest;
  60: 
  61: elem *esharedctor;
  62: SharedStaticDtorDeclarations esharedctorgates;
  63: elem *eshareddtor;
  64: 
  65: int dtorcount;
  66: int shareddtorcount;
  67: 
  68: char *lastmname;
  69: 
  70: /**************************************
  71:  * Append s to list of object files to generate later.
  72:  */
  73: 
  74: Dsymbols obj_symbols_towrite;
  75: 
  76: void obj_append(Dsymbol *s)
  77: {
  78:     obj_symbols_towrite.push(s);
  79: }
  80: 
  81: void obj_write_deferred(Library *library)
  82: {
  83:     for (int i = 0; i < obj_symbols_towrite.dim; i++)
warning C4018: '<' : signed/unsigned mismatch
84: { Dsymbol *s = obj_symbols_towrite.tdata()[i]; 85: Module *m = s->getModule(); 86: 87: char *mname; 88: if (m) 89: { mname = m->srcfile->toChars(); 90: lastmname = mname; 91: } 92: else 93: { 94: //mname = s->ident->toChars(); 95: mname = lastmname; 96: assert(mname); 97: } 98: 99: obj_start(mname); 100: 101: static int count; 102: count++; // sequence for generating names 103: 104: /* Create a module that's a doppelganger of m, with just 105: * enough to be able to create the moduleinfo. 106: */ 107: OutBuffer idbuf; 108: idbuf.printf("%s.%d", m ? m->ident->toChars() : mname, count); 109: char *idstr = idbuf.toChars(); 110: idbuf.data = NULL; 111: Identifier *id = new Identifier(idstr, TOKidentifier); 112: 113: Module *md = new Module(mname, id, 0, 0);
warning C6211: Leaking memory 'md' due to an exception. Consider using a local catch block to clean up memory: Lines: 83, 84, 85, 87, 88, 89, 90, 99, 101, 102, 107, 108, 109, 110, 111, 113, 114
114: md->members = new Dsymbols(); 115: md->members->push(s); // its only 'member' is s 116: if (m) 117: { 118: md->doppelganger = 1; // identify this module as doppelganger 119: md->md = m->md; 120: md->aimports.push(m); // it only 'imports' m 121: md->massert = m->massert; 122: md->munittest = m->munittest; 123: md->marray = m->marray; 124: } 125: 126: md->genobjfile(0); 127: 128: /* Set object file name to be source name with sequence number, 129: * as mangled symbol names get way too long. 130: */ 131: char *fname = FileName::removeExt(mname); 132: OutBuffer namebuf; 133: unsigned hash = 0; 134: for (char *p = s->toChars(); *p; p++) 135: hash += *p; 136: namebuf.printf("%s_%x_%x.%s", fname, count, hash, global.obj_ext); 137: namebuf.writeByte(0); 138: mem.free(fname); 139: fname = (char *)namebuf.extractData(); 140: 141: //printf("writing '%s'\n", fname); 142: File *objfile = new File(fname); 143: obj_end(library, objfile); 144: } 145: obj_symbols_towrite.dim = 0; 146: } 147: 148: /************************************** 149: * Prepare for generating obj file. 150: */ 151: 152: Outbuffer objbuf; 153: 154: void obj_start(char *srcfile) 155: { 156: //printf("obj_start()\n"); 157: 158: out_config_init(); 159: 160: rtlsym_reset(); 161: slist_reset(); 162: clearStringTab(); 163: 164: obj_init(&objbuf, srcfile, NULL); 165: 166: el_reset(); 167: cg87_reset(); 168: out_reset(); 169: } 170: 171: void obj_end(Library *library, File *objfile) 172: { 173: obj_term(); 174: 175: if (library) 176: { 177: // Transfer image to library 178: library->addObject(objfile->name->toChars(), objbuf.buf, objbuf.p - objbuf.buf); 179: objbuf.buf = NULL; 180: } 181: else 182: { 183: // Transfer image to file 184: objfile->setbuffer(objbuf.buf, objbuf.p - objbuf.buf); 185: objbuf.buf = NULL; 186: 187: char *p = FileName::path(objfile->name->toChars()); 188: FileName::ensurePathExists(p); 189: //mem.free(p); 190: 191: //printf("write obj %s\n", objfile->name->toChars()); 192: objfile->writev(); 193: } 194: objbuf.pend = NULL; 195: objbuf.p = NULL; 196: objbuf.len = 0; 197: objbuf.inc = 0; 198: } 199: 200: /************************************** 201: * Generate .obj file for Module. 202: */ 203: 204: void Module::genobjfile(int multiobj) 205: { 206: //EEcontext *ee = env->getEEcontext(); 207: 208: //printf("Module::genobjfile(multiobj = %d) %s\n", multiobj, toChars()); 209: 210: lastmname = srcfile->toChars(); 211: 212: obj_initfile(lastmname, NULL, toPrettyChars()); 213: 214: eictor = NULL; 215: ictorlocalgot = NULL; 216: ector = NULL; 217: ectorgates.setDim(0); 218: edtor = NULL; 219: esharedctor = NULL; 220: esharedctorgates.setDim(0); 221: eshareddtor = NULL; 222: etest = NULL; 223: dtorcount = 0; 224: shareddtorcount = 0; 225: 226: if (doppelganger) 227: { 228: /* Generate a reference to the moduleinfo, so the module constructors 229: * and destructors get linked in. 230: */ 231: Module *m = aimports.tdata()[0]; 232: assert(m); 233: if (m->sictor || m->sctor || m->sdtor || m->ssharedctor || m->sshareddtor) 234: { 235: Symbol *s = m->toSymbol(); 236: //objextern(s); 237: //if (!s->Sxtrnnum) objextdef(s->Sident); 238: if (!s->Sxtrnnum) 239: { 240: //printf("%s\n", s->Sident); 241: #if 0 /* This should work, but causes optlink to fail in common/newlib.asm */ 242: objextdef(s->Sident); 243: #else 244: #if ELFOBJ || MACHOBJ 245: int nbytes = reftoident(DATA, Offset(DATA), s, 0, CFoff); 246: Offset(DATA) += nbytes; 247: #else 248: int nbytes = reftoident(DATA, Doffset, s, 0, CFoff); 249: Doffset += nbytes; 250: #endif 251: #endif 252: } 253: } 254: } 255: 256: if (global.params.cov) 257: { 258: /* Create coverage identifier: 259: * private uint[numlines] __coverage; 260: */ 261: cov = symbol_calloc("__coverage"); 262: cov->Stype = type_fake(TYint); 263: cov->Stype->Tmangle = mTYman_c; 264: cov->Stype->Tcount++; 265: cov->Sclass = SCstatic; 266: cov->Sfl = FLdata; 267: #if ELFOBJ || MACHOBJ 268: cov->Sseg = UDATA; 269: #endif 270: dtnzeros(&cov->Sdt, 4 * numlines); 271: outdata(cov); 272: slist_add(cov); 273: 274: covb = (unsigned *)calloc((numlines + 32) / 32, sizeof(*covb)); 275: } 276: 277: for (int i = 0; i < members->dim; i++)
warning C4018: '<' : signed/unsigned mismatch
278: { 279: Dsymbol *member = members->tdata()[i]; 280: member->toObjFile(multiobj); 281: } 282: 283: if (global.params.cov) 284: { 285: /* Generate 286: * bit[numlines] __bcoverage; 287: */ 288: Symbol *bcov = symbol_calloc("__bcoverage"); 289: bcov->Stype = type_fake(TYuint); 290: bcov->Stype->Tcount++; 291: bcov->Sclass = SCstatic; 292: bcov->Sfl = FLdata; 293: #if ELFOBJ || MACHOBJ 294: bcov->Sseg = DATA; 295: #endif 296: dtnbytes(&bcov->Sdt, (numlines + 32) / 32 * sizeof(*covb), (char *)covb); 297: outdata(bcov); 298: 299: free(covb); 300: covb = NULL; 301: 302: /* Generate: 303: * _d_cover_register(uint[] __coverage, BitArray __bcoverage, string filename); 304: * and prepend it to the static constructor. 305: */ 306: 307: /* t will be the type of the functions generated: 308: * extern (C) void func(); 309: */ 310: type *t = type_alloc(TYnfunc); 311: t->Tflags |= TFprototype | TFfixed; 312: t->Tmangle = mTYman_c; 313: t->Tnext = tsvoid; 314: tsvoid->Tcount++; 315: 316: sictor = toSymbolX("__modictor", SCglobal, t, "FZv"); 317: cstate.CSpsymtab = &sictor->Sfunc->Flocsym; 318: localgot = ictorlocalgot; 319: elem *e; 320: 321: e = el_params(el_pair(TYdarray, el_long(TYsize_t, numlines), el_ptr(cov)), 322: el_pair(TYdarray, el_long(TYsize_t, numlines), el_ptr(bcov)), 323: toEfilename(), 324: NULL); 325: e = el_bin(OPcall, TYvoid, el_var(rtlsym[RTLSYM_DCOVER]), e); 326: eictor = el_combine(e, eictor); 327: ictorlocalgot = localgot; 328: } 329: 330: // If coverage / static constructor / destructor / unittest calls 331: if (eictor || ector || ectorgates.dim || edtor || 332: esharedctor || esharedctorgates.dim || eshareddtor || etest) 333: { 334: /* t will be the type of the functions generated: 335: * extern (C) void func(); 336: */ 337: type *t = type_alloc(TYnfunc); 338: t->Tflags |= TFprototype | TFfixed; 339: t->Tmangle = mTYman_c; 340: t->Tnext = tsvoid; 341: tsvoid->Tcount++; 342: 343: static char moddeco[] = "FZv"; 344: 345: if (eictor) 346: { 347: localgot = ictorlocalgot; 348: 349: block *b = block_calloc(); 350: b->BC = BCret; 351: b->Belem = eictor; 352: sictor->Sfunc->Fstartline.Sfilename = arg; 353: sictor->Sfunc->Fstartblock = b; 354: writefunc(sictor); 355: } 356: 357: if (ector || ectorgates.dim) 358: { 359: localgot = NULL; 360: sctor = toSymbolX("__modctor", SCglobal, t, moddeco); 361: #if DMDV2 362: cstate.CSpsymtab = &sctor->Sfunc->Flocsym; 363: 364: for (int i = 0; i < ectorgates.dim; i++)
warning C4018: '<' : signed/unsigned mismatch
365: { StaticDtorDeclaration *f = ectorgates.tdata()[i]; 366: 367: Symbol *s = f->vgate->toSymbol(); 368: elem *e = el_var(s); 369: e = el_bin(OPaddass, TYint, e, el_long(TYint, 1)); 370: ector = el_combine(ector, e); 371: } 372: #endif 373: 374: block *b = block_calloc(); 375: b->BC = BCret; 376: b->Belem = ector; 377: sctor->Sfunc->Fstartline.Sfilename = arg; 378: sctor->Sfunc->Fstartblock = b; 379: writefunc(sctor); 380: #if STATICCTOR 381: obj_staticctor(sctor, dtorcount, 1); 382: #endif 383: } 384: 385: if (edtor) 386: { 387: localgot = NULL; 388: sdtor = toSymbolX("__moddtor", SCglobal, t, moddeco); 389: 390: block *b = block_calloc(); 391: b->BC = BCret; 392: b->Belem = edtor; 393: sdtor->Sfunc->Fstartline.Sfilename = arg; 394: sdtor->Sfunc->Fstartblock = b; 395: writefunc(sdtor); 396: } 397: 398: #if DMDV2 399: if (esharedctor || esharedctorgates.dim) 400: { 401: localgot = NULL; 402: ssharedctor = toSymbolX("__modsharedctor", SCglobal, t, moddeco); 403: cstate.CSpsymtab = &ssharedctor->Sfunc->Flocsym; 404: 405: for (int i = 0; i < esharedctorgates.dim; i++)
warning C4018: '<' : signed/unsigned mismatch
406: { SharedStaticDtorDeclaration *f = esharedctorgates.tdata()[i]; 407: 408: Symbol *s = f->vgate->toSymbol(); 409: elem *e = el_var(s); 410: e = el_bin(OPaddass, TYint, e, el_long(TYint, 1)); 411: esharedctor = el_combine(esharedctor, e); 412: } 413: 414: block *b = block_calloc(); 415: b->BC = BCret; 416: b->Belem = esharedctor; 417: ssharedctor->Sfunc->Fstartline.Sfilename = arg; 418: ssharedctor->Sfunc->Fstartblock = b; 419: writefunc(ssharedctor); 420: #if STATICCTOR 421: obj_staticctor(ssharedctor, shareddtorcount, 1); 422: #endif 423: } 424: 425: if (eshareddtor) 426: { 427: localgot = NULL; 428: sshareddtor = toSymbolX("__modshareddtor", SCglobal, t, moddeco); 429: 430: block *b = block_calloc(); 431: b->BC = BCret; 432: b->Belem = eshareddtor; 433: sshareddtor->Sfunc->Fstartline.Sfilename = arg; 434: sshareddtor->Sfunc->Fstartblock = b; 435: writefunc(sshareddtor); 436: } 437: #endif 438: 439: if (etest) 440: { 441: localgot = NULL; 442: stest = toSymbolX("__modtest", SCglobal, t, moddeco); 443: 444: block *b = block_calloc(); 445: b->BC = BCret; 446: b->Belem = etest; 447: stest->Sfunc->Fstartline.Sfilename = arg; 448: stest->Sfunc->Fstartblock = b; 449: writefunc(stest); 450: } 451: 452: if (doppelganger) 453: genmoduleinfo(); 454: } 455: 456: if (doppelganger) 457: { 458: obj_termfile(); 459: return; 460: } 461: 462: if (global.params.multiobj) 463: { /* This is necessary because the main .obj for this module is written 464: * first, but determining whether marray or massert or munittest are needed is done 465: * possibly later in the doppelganger modules. 466: * Another way to fix it is do the main one last. 467: */ 468: toModuleAssert(); 469: toModuleUnittest(); 470: toModuleArray(); 471: } 472: 473: #if 1 474: // Always generate module info, because of templates and -cov 475: if (1 || needModuleInfo())
warning C6286: (<non-zero constant> || <expression>) is always a non-zero constant. <expression> is never evaluated and might have side effects
476: genmoduleinfo(); 477: #endif 478: 479: // If module assert 480: for (int i = 0; i < 3; i++) 481: { 482: Symbol *ma; 483: unsigned rt; 484: unsigned bc; 485: switch (i) 486: { 487: case 0: ma = marray; rt = RTLSYM_DARRAY; bc = BCexit; break; 488: case 1: ma = massert; rt = RTLSYM_DASSERTM; bc = BCexit; break; 489: case 2: ma = munittest; rt = RTLSYM_DUNITTESTM; bc = BCret; break; 490: default: assert(0); 491: } 492: 493: if (ma) 494: { 495: elem *elinnum; 496: 497: localgot = NULL; 498: 499: // Call dassert(filename, line) 500: // Get sole parameter, linnum 501: { 502: Symbol *sp = symbol_calloc("linnum"); 503: sp->Stype = type_fake(TYint); 504: sp->Stype->Tcount++; 505: sp->Sclass = SCfastpar; 506: sp->Spreg = I64 ? DI : AX; 507: sp->Sflags &= ~SFLspill; 508: sp->Sfl = FLpara; // FLauto? 509: cstate.CSpsymtab = &ma->Sfunc->Flocsym; 510: symbol_add(sp); 511: 512: elinnum = el_var(sp); 513: } 514: 515: elem *efilename = el_ptr(toSymbol()); 516: 517: elem *e = el_var(rtlsym[rt]); 518: e = el_bin(OPcall, TYvoid, e, el_param(elinnum, efilename)); 519: 520: block *b = block_calloc(); 521: b->BC = bc; 522: b->Belem = e; 523: ma->Sfunc->Fstartline.Sfilename = arg; 524: ma->Sfunc->Fstartblock = b; 525: ma->Sclass = SCglobal; 526: ma->Sfl = 0; 527: ma->Sflags |= rtlsym[rt]->Sflags & SFLexit; 528: writefunc(ma); 529: } 530: } 531: 532: obj_termfile(); 533: } 534: 535: 536: /* ================================================================== */ 537: 538: void FuncDeclaration::toObjFile(int multiobj) 539: { 540: Symbol *senter;
warning C4101: 'senter' : unreferenced local variable
541: Symbol *sexit;
warning C4101: 'sexit' : unreferenced local variable
542: FuncDeclaration *func = this; 543: ClassDeclaration *cd = func->parent->isClassDeclaration(); 544: int reverse; 545: int i; 546: int has_arguments; 547: 548: //printf("FuncDeclaration::toObjFile(%p, %s.%s)\n", func, parent->toChars(), func->toChars()); 549: //if (type) printf("type = %s\n", func->type->toChars()); 550: #if 0 551: //printf("line = %d\n",func->getWhere() / LINEINC); 552: EEcontext *ee = env->getEEcontext(); 553: if (ee->EEcompile == 2) 554: { 555: if (ee->EElinnum < (func->getWhere() / LINEINC) || 556: ee->EElinnum > (func->endwhere / LINEINC) 557: ) 558: return; // don't compile this function 559: ee->EEfunc = func->toSymbol(); 560: } 561: #endif 562: 563: if (semanticRun >= PASSobj) // if toObjFile() already run 564: return; 565: 566: // If errors occurred compiling it, such as bugzilla 6118 567: if (type && type->ty == Tfunction && ((TypeFunction *)type)->next->ty == Terror) 568: return; 569: 570: if (!func->fbody) 571: { 572: return; 573: } 574: if (func->isUnitTestDeclaration() && !global.params.useUnitTests) 575: return; 576: 577: if (multiobj && !isStaticDtorDeclaration() && !isStaticCtorDeclaration()) 578: { obj_append(this); 579: return; 580: } 581: 582: assert(semanticRun == PASSsemantic3done); 583: semanticRun = PASSobj; 584: 585: if (global.params.verbose) 586: printf("function %s\n",func->toChars()); 587: 588: Symbol *s = func->toSymbol(); 589: func_t *f = s->Sfunc; 590: 591: #if TARGET_WINDOS 592: /* This is done so that the 'this' pointer on the stack is the same 593: * distance away from the function parameters, so that an overriding 594: * function can call the nested fdensure or fdrequire of its overridden function 595: * and the stack offsets are the same. 596: */ 597: if (isVirtual() && (fensure || frequire)) 598: f->Fflags3 |= Ffakeeh; 599: #endif 600: 601: #if TARGET_OSX 602: s->Sclass = SCcomdat; 603: #else 604: s->Sclass = SCglobal; 605: #endif 606: for (Dsymbol *p = parent; p; p = p->parent) 607: { 608: if (p->isTemplateInstance()) 609: { 610: s->Sclass = SCcomdat; 611: break; 612: } 613: } 614: 615: /* Vector operations should be comdat's 616: */ 617: if (isArrayOp) 618: s->Sclass = SCcomdat; 619: 620: if (isNested()) 621: { 622: // if (!(config.flags3 & CFG3pic)) 623: // s->Sclass = SCstatic; 624: f->Fflags3 |= Fnested; 625: } 626: else 627: { 628: const char *libname = (global.params.symdebug) 629: ? global.params.debuglibname 630: : global.params.defaultlibname; 631: 632: // Pull in RTL startup code 633: if (func->isMain()) 634: { objextdef("_main"); 635: #if TARGET_LINUX || TARGET_OSX || TARGET_FREEBSD || TARGET_OPENBSD || TARGET_SOLARIS 636: obj_ehsections(); // initialize exception handling sections 637: #endif 638: #if TARGET_WINDOS 639: objextdef("__acrtused_con"); 640: #endif 641: obj_includelib(libname); 642: s->Sclass = SCglobal; 643: } 644: else if (strcmp(s->Sident, "main") == 0 && linkage == LINKc) 645: { 646: #if TARGET_WINDOS 647: objextdef("__acrtused_con"); // bring in C startup code 648: obj_includelib("snn.lib"); // bring in C runtime library 649: #endif 650: s->Sclass = SCglobal; 651: } 652: else if (func->isWinMain()) 653: { 654: objextdef("__acrtused"); 655: obj_includelib(libname); 656: s->Sclass = SCglobal; 657: } 658: 659: // Pull in RTL startup code 660: else if (func->isDllMain()) 661: { 662: objextdef("__acrtused_dll"); 663: obj_includelib(libname); 664: s->Sclass = SCglobal; 665: } 666: } 667: 668: cstate.CSpsymtab = &f->Flocsym; 669: 670: // Find module m for this function 671: Module *m = NULL; 672: for (Dsymbol *p = parent; p; p = p->parent) 673: { 674: m = p->isModule(); 675: if (m) 676: break; 677: } 678: 679: IRState irs(m, func); 680: Dsymbols deferToObj; // write these to OBJ file later 681: irs.deferToObj = &deferToObj; 682: 683: TypeFunction *tf; 684: enum RET retmethod; 685: symbol *shidden = NULL; 686: Symbol *sthis = NULL; 687: tym_t tyf; 688: 689: tyf = tybasic(s->Stype->Tty); 690: //printf("linkage = %d, tyf = x%x\n", linkage, tyf); 691: reverse = tyrevfunc(s->Stype->Tty); 692: 693: assert(func->type->ty == Tfunction); 694: tf = (TypeFunction *)(func->type); 695: has_arguments = (tf->linkage == LINKd) && (tf->varargs == 1); 696: retmethod = tf->retStyle(); 697: if (retmethod == RETstack) 698: { 699: // If function returns a struct, put a pointer to that 700: // as the first argument 701: ::type *thidden = tf->next->pointerTo()->toCtype(); 702: char hiddenparam[5+4+1]; 703: static int hiddenparami; // how many we've generated so far 704: 705: sprintf(hiddenparam,"__HID%d",++hiddenparami);
warning C4996: 'sprintf': This function or variable may be unsafe. Consider using sprintf_s instead. To disable deprecation, use _CRT_SECURE_NO_WARNINGS. See online help for details. c:\Program Files (x86)\Microsoft Visual Studio 10.0\VC\include\stdio.h(371) : see declaration of 'sprintf'
706: shidden = symbol_name(hiddenparam,SCparameter,thidden); 707: shidden->Sflags |= SFLtrue | SFLfree; 708: #if DMDV1 709: if (func->nrvo_can && func->nrvo_var && func->nrvo_var->nestedref) 710: #else 711: if (func->nrvo_can && func->nrvo_var && func->nrvo_var->nestedrefs.dim) 712: #endif 713: type_setcv(&shidden->Stype, shidden->Stype->Tty | mTYvolatile); 714: irs.shidden = shidden; 715: this->shidden = shidden; 716: } 717: 718: if (vthis) 719: { 720: assert(!vthis->csym); 721: sthis = vthis->toSymbol(); 722: irs.sthis = sthis; 723: if (!(f->Fflags3 & Fnested)) 724: f->Fflags3 |= Fmember; 725: } 726: 727: Symbol **params; 728: unsigned pi; 729: 730: // Estimate number of parameters, pi 731: pi = (v_arguments != NULL); 732: if (parameters) 733: pi += parameters->dim; 734: // Allow extra 2 for sthis and shidden 735: params = (Symbol **)alloca((pi + 2) * sizeof(Symbol *));
warning C6255: _alloca indicates failure by raising a stack overflow exception. Consider using _malloca instead
736: 737: // Get the actual number of parameters, pi, and fill in the params[] 738: pi = 0; 739: if (v_arguments) 740: { 741: params[pi] = v_arguments->toSymbol(); 742: pi += 1; 743: } 744: if (parameters) 745: { 746: for (i = 0; i < parameters->dim; i++)
warning C4018: '<' : signed/unsigned mismatch
747: { VarDeclaration *v = parameters->tdata()[i]; 748: if (v->csym) 749: { 750: error("compiler error, parameter '%s', bugzilla 2962?", v->toChars()); 751: assert(0); 752: } 753: params[pi + i] = v->toSymbol(); 754: } 755: pi += i; 756: } 757: 758: if (reverse) 759: { // Reverse params[] entries 760: for (i = 0; i < pi/2; i++)
warning C4018: '<' : signed/unsigned mismatch
761: { 762: Symbol *sptmp = params[i]; 763: params[i] = params[pi - 1 - i]; 764: params[pi - 1 - i] = sptmp; 765: } 766: } 767: 768: if (shidden) 769: { 770: #if 0 771: // shidden becomes last parameter 772: params[pi] = shidden; 773: #else 774: // shidden becomes first parameter 775: memmove(params + 1, params, pi * sizeof(params[0])); 776: params[0] = shidden; 777: #endif 778: pi++; 779: } 780: 781: 782: if (sthis) 783: { 784: #if 0 785: // sthis becomes last parameter 786: params[pi] = sthis; 787: #else 788: // sthis becomes first parameter 789: memmove(params + 1, params, pi * sizeof(params[0])); 790: params[0] = sthis; 791: #endif 792: pi++; 793: } 794: 795: if ((global.params.isLinux || global.params.isOSX || global.params.isFreeBSD || global.params.isSolaris) && 796: linkage != LINKd && shidden && sthis) 797: { 798: /* swap shidden and sthis 799: */ 800: Symbol *sp = params[0]; 801: params[0] = params[1]; 802: params[1] = sp; 803: } 804: 805: for (i = 0; i < pi; i++)
warning C4018: '<' : signed/unsigned mismatch
806: { Symbol *sp = params[i]; 807: sp->Sclass = SCparameter; 808: sp->Sflags &= ~SFLspill; 809: sp->Sfl = FLpara; 810: symbol_add(sp); 811: } 812: 813: // Determine register assignments 814: if (pi) 815: { 816: if (global.params.is64bit) 817: { 818: // Order of assignment of pointer or integer parameters 819: static const unsigned char argregs[6] = { DI,SI,DX,CX,R8,R9 }; 820: int r = 0; 821: int xmmcnt = XMM0; 822: 823: for (int i = 0; i < pi; i++)
warning C4018: '<' : signed/unsigned mismatch
warning C6246: Local declaration of 'i' hides declaration of the same name in outer scope. For additional information, see previous declaration at line '545' of 'c:\projects\extern\d\dmd\src\glue.c': Lines: 545
824: { Symbol *sp = params[i]; 825: tym_t ty = tybasic(sp->Stype->Tty); 826: // BUG: doesn't work for structs 827: if (r < sizeof(argregs)/sizeof(argregs[0])) 828: { 829: if (type_jparam(sp->Stype)) 830: { 831: sp->Sclass = SCfastpar; 832: sp->Spreg = argregs[r]; 833: sp->Sfl = FLauto; 834: ++r; 835: } 836: } 837: if (xmmcnt < XMM7) 838: { 839: if (tyfloating(ty) && tysize(ty) <= 8) 840: { 841: sp->Sclass = SCfastpar; 842: sp->Spreg = xmmcnt; 843: sp->Sfl = FLauto; 844: ++xmmcnt; 845: } 846: } 847: } 848: } 849: else 850: { 851: // First parameter goes in register 852: Symbol *sp = params[0]; 853: if ((tyf == TYjfunc || tyf == TYmfunc) && 854: type_jparam(sp->Stype)) 855: { sp->Sclass = SCfastpar; 856: sp->Spreg = (tyf == TYjfunc) ? AX : CX; 857: sp->Sfl = FLauto; 858: //printf("'%s' is SCfastpar\n",sp->Sident); 859: } 860: } 861: } 862: 863: if (func->fbody) 864: { block *b; 865: Blockx bx; 866: Statement *sbody; 867: 868: localgot = NULL; 869: 870: sbody = func->fbody; 871: memset(&bx,0,sizeof(bx)); 872: bx.startblock = block_calloc(); 873: bx.curblock = bx.startblock; 874: bx.funcsym = s; 875: bx.scope_index = -1; 876: bx.classdec = cd; 877: bx.member = func; 878: bx.module = getModule(); 879: irs.blx = &bx; 880: #if DMDV2 881: buildClosure(&irs); 882: #endif 883: 884: #if 0 885: if (func->isSynchronized()) 886: { 887: if (cd) 888: { elem *esync; 889: if (func->isStatic()) 890: { // monitor is in ClassInfo 891: esync = el_ptr(cd->toSymbol()); 892: } 893: else 894: { // 'this' is the monitor 895: esync = el_var(sthis); 896: } 897: 898: if (func->isStatic() || sbody->usesEH() || 899: !(config.flags2 & CFG2seh)) 900: { // BUG: what if frequire or fensure uses EH? 901: 902: sbody = new SynchronizedStatement(func->loc, esync, sbody); 903: } 904: else 905: { 906: #if TARGET_WINDOS 907: if (config.flags2 & CFG2seh) 908: { 909: /* The "jmonitor" uses an optimized exception handling frame 910: * which is a little shorter than the more general EH frame. 911: * It isn't strictly necessary. 912: */ 913: s->Sfunc->Fflags3 |= Fjmonitor; 914: } 915: #endif 916: el_free(esync); 917: } 918: } 919: else 920: { 921: error("synchronized function %s must be a member of a class", func->toChars()); 922: } 923: } 924: #elif TARGET_WINDOS 925: if (func->isSynchronized() && cd && config.flags2 & CFG2seh && 926: !func->isStatic() && !sbody->usesEH()) 927: { 928: /* The "jmonitor" hack uses an optimized exception handling frame 929: * which is a little shorter than the more general EH frame. 930: */ 931: s->Sfunc->Fflags3 |= Fjmonitor; 932: } 933: #endif 934: 935: sbody->toIR(&irs); 936: bx.curblock->BC = BCret; 937: 938: f->Fstartblock = bx.startblock; 939: // einit = el_combine(einit,bx.init); 940: 941: if (isCtorDeclaration()) 942: { 943: assert(sthis); 944: for (b = f->Fstartblock; b; b = b->Bnext) 945: { 946: if (b->BC == BCret) 947: { 948: b->BC = BCretexp; 949: b->Belem = el_combine(b->Belem, el_var(sthis)); 950: } 951: } 952: } 953: } 954: 955: // If static constructor 956: #if DMDV2 957: if (isSharedStaticCtorDeclaration()) // must come first because it derives from StaticCtorDeclaration 958: { 959: elem *e = el_una(OPucall, TYvoid, el_var(s)); 960: esharedctor = el_combine(esharedctor, e); 961: } 962: else 963: #endif 964: if (isStaticCtorDeclaration()) 965: { 966: elem *e = el_una(OPucall, TYvoid, el_var(s)); 967: ector = el_combine(ector, e); 968: } 969: 970: // If static destructor 971: #if DMDV2 972: if (isSharedStaticDtorDeclaration()) // must come first because it derives from StaticDtorDeclaration 973: { 974: elem *e; 975: 976: #if STATICCTOR 977: e = el_bin(OPcall, TYvoid, el_var(rtlsym[RTLSYM_FATEXIT]), el_ptr(s)); 978: esharedctor = el_combine(esharedctor, e); 979: shareddtorcount++; 980: #else 981: SharedStaticDtorDeclaration *f = isSharedStaticDtorDeclaration();
warning C6246: Local declaration of 'f' hides declaration of the same name in outer scope. For additional information, see previous declaration at line '589' of 'c:\projects\extern\d\dmd\src\glue.c': Lines: 589
982: assert(f); 983: if (f->vgate) 984: { /* Increment destructor's vgate at construction time 985: */ 986: esharedctorgates.push(f); 987: } 988: 989: e = el_una(OPucall, TYvoid, el_var(s)); 990: eshareddtor = el_combine(e, eshareddtor); 991: #endif 992: } 993: else 994: #endif 995: if (isStaticDtorDeclaration()) 996: { 997: elem *e; 998: 999: #if STATICCTOR 1000: e = el_bin(OPcall, TYvoid, el_var(rtlsym[RTLSYM_FATEXIT]), el_ptr(s)); 1001: ector = el_combine(ector, e); 1002: dtorcount++; 1003: #else 1004: StaticDtorDeclaration *f = isStaticDtorDeclaration();
warning C6246: Local declaration of 'f' hides declaration of the same name in outer scope. For additional information, see previous declaration at line '589' of 'c:\projects\extern\d\dmd\src\glue.c': Lines: 589
1005: assert(f); 1006: if (f->vgate) 1007: { /* Increment destructor's vgate at construction time 1008: */ 1009: ectorgates.push(f); 1010: } 1011: 1012: e = el_una(OPucall, TYvoid, el_var(s)); 1013: edtor = el_combine(e, edtor); 1014: #endif 1015: } 1016: 1017: // If unit test 1018: if (isUnitTestDeclaration()) 1019: { 1020: elem *e = el_una(OPucall, TYvoid, el_var(s)); 1021: etest = el_combine(etest, e); 1022: } 1023: 1024: if (global.errors) 1025: return; 1026: 1027: writefunc(s); 1028: if (isExport()) 1029: obj_export(s, Poffset); 1030: 1031: for (i = 0; i < irs.deferToObj->dim; i++)
warning C4018: '<' : signed/unsigned mismatch
1032: { 1033: Dsymbol *s = irs.deferToObj->tdata()[i];
warning C6246: Local declaration of 's' hides declaration of the same name in outer scope. For additional information, see previous declaration at line '588' of 'c:\projects\extern\d\dmd\src\glue.c': Lines: 588
1034: s->toObjFile(0); 1035: } 1036: 1037: #if TARGET_LINUX || TARGET_OSX || TARGET_FREEBSD || TARGET_OPENBSD || TARGET_SOLARIS 1038: // A hack to get a pointer to this function put in the .dtors segment 1039: if (ident && memcmp(ident->toChars(), "_STD", 4) == 0) 1040: obj_staticdtor(s); 1041: #endif 1042: #if DMDV2 1043: if (irs.startaddress) 1044: { 1045: printf("Setting start address\n"); 1046: obj_startaddress(irs.startaddress); 1047: } 1048: #endif 1049: } 1050: 1051: /* ================================================================== */ 1052: 1053: /***************************** 1054: * Return back end type corresponding to D front end type. 1055: */ 1056: 1057: unsigned Type::totym() 1058: { unsigned t; 1059: 1060: switch (ty) 1061: { 1062: case Tvoid: t = TYvoid; break; 1063: case Tint8: t = TYschar; break; 1064: case Tuns8: t = TYuchar; break; 1065: case Tint16: t = TYshort; break; 1066: case Tuns16: t = TYushort; break; 1067: case Tint32: t = TYint; break; 1068: case Tuns32: t = TYuint; break; 1069: case Tint64: t = TYllong; break; 1070: case Tuns64: t = TYullong; break; 1071: case Tfloat32: t = TYfloat; break; 1072: case Tfloat64: t = TYdouble; break; 1073: case Tfloat80: t = TYldouble; break; 1074: case Timaginary32: t = TYifloat; break; 1075: case Timaginary64: t = TYidouble; break; 1076: case Timaginary80: t = TYildouble; break; 1077: case Tcomplex32: t = TYcfloat; break; 1078: case Tcomplex64: t = TYcdouble; break; 1079: case Tcomplex80: t = TYcldouble; break; 1080: case Tbool: t = TYbool; break; 1081: case Tchar: t = TYchar; break; 1082: #if TARGET_LINUX || TARGET_OSX || TARGET_FREEBSD || TARGET_OPENBSD || TARGET_SOLARIS 1083: case Twchar: t = TYwchar_t; break; 1084: case Tdchar: t = TYdchar; break; 1085: #else 1086: case Twchar: t = TYwchar_t; break; 1087: case Tdchar: 1088: t = (global.params.symdebug == 1) ? TYdchar : TYulong; 1089: break; 1090: #endif 1091: 1092: case Taarray: t = TYaarray; break; 1093: case Tclass: 1094: case Treference: 1095: case Tpointer: t = TYnptr; break; 1096: case Tdelegate: t = TYdelegate; break; 1097: case Tarray: t = TYdarray; break; 1098: #if SARRAYVALUE 1099: case Tsarray: t = TYstruct; break; 1100: #else 1101: case Tsarray: t = TYarray; break; 1102: #endif 1103: case Tstruct: t = TYstruct; break; 1104: 1105: case Tenum: 1106: case Ttypedef: 1107: t = toBasetype()->totym(); 1108: break; 1109: 1110: case Tident: 1111: case Ttypeof: 1112: #ifdef DEBUG 1113: printf("ty = %d, '%s'\n", ty, toChars()); 1114: #endif 1115: error(0, "forward reference of %s", toChars()); 1116: t = TYint; 1117: break; 1118: 1119: default: 1120: #ifdef DEBUG 1121: printf("ty = %d, '%s'\n", ty, toChars()); 1122: halt(); 1123: #endif 1124: assert(0); 1125: } 1126: 1127: #if DMDV2 1128: // Add modifiers 1129: switch (mod) 1130: { 1131: case 0: 1132: break; 1133: case MODconst: 1134: case MODwild: 1135: t |= mTYconst; 1136: break; 1137: case MODimmutable: 1138: t |= mTYimmutable; 1139: break; 1140: case MODshared: 1141: t |= mTYshared; 1142: break; 1143: case MODshared | MODwild: 1144: case MODshared | MODconst: 1145: t |= mTYshared | mTYconst; 1146: break; 1147: default: 1148: assert(0); 1149: } 1150: #endif 1151: 1152: return t; 1153: } 1154: 1155: unsigned TypeFunction::totym() 1156: { 1157: tym_t tyf; 1158: 1159: //printf("TypeFunction::totym(), linkage = %d\n", linkage); 1160: switch (linkage) 1161: { 1162: case LINKwindows: 1163: tyf = (varargs == 1) ? TYnfunc : TYnsfunc; 1164: break; 1165: 1166: case LINKpascal: 1167: tyf = (varargs == 1) ? TYnfunc : TYnpfunc; 1168: break; 1169: 1170: case LINKc: 1171: tyf = TYnfunc; 1172: #if TARGET_LINUX || TARGET_OSX || TARGET_FREEBSD || TARGET_OPENBSD || TARGET_SOLARIS 1173: if (I32 && retStyle() == RETstack) 1174: tyf = TYhfunc; 1175: #endif 1176: break; 1177: 1178: case LINKd: 1179: tyf = (varargs == 1) ? TYnfunc : TYjfunc; 1180: break; 1181: 1182: case LINKcpp: 1183: tyf = TYnfunc; 1184: break; 1185: 1186: default: 1187: printf("linkage = %d\n", linkage); 1188: assert(0); 1189: } 1190: #if DMDV2 1191: if (isnothrow) 1192: tyf |= mTYnothrow; 1193: #endif 1194: return tyf; 1195: } 1196: 1197: /************************************** 1198: */ 1199: 1200: Symbol *Type::toSymbol() 1201: { 1202: assert(0); 1203: return NULL; 1204: } 1205: 1206: Symbol *TypeClass::toSymbol() 1207: { 1208: return sym->toSymbol(); 1209: } 1210: 1211: /************************************* 1212: * Generate symbol in data segment for critical section. 1213: */ 1214: 1215: Symbol *Module::gencritsec() 1216: { 1217: Symbol *s; 1218: type *t; 1219: 1220: t = Type::tint32->toCtype(); 1221: s = symbol_name("critsec", SCstatic, t); 1222: s->Sfl = FLdata; 1223: /* Must match D_CRITICAL_SECTION in phobos/internal/critical.c 1224: */ 1225: dtnzeros(&s->Sdt, PTRSIZE + (I64 ? os_critsecsize64() : os_critsecsize32())); 1226: #if ELFOBJ || MACHOBJ // Burton 1227: s->Sseg = DATA; 1228: #endif 1229: outdata(s); 1230: return s; 1231: } 1232: 1233: /************************************** 1234: * Generate elem that is a pointer to the module file name. 1235: */ 1236: 1237: elem *Module::toEfilename() 1238: { elem *efilename; 1239: 1240: if (!sfilename) 1241: { 1242: dt_t *dt = NULL; 1243: char *id; 1244: int len; 1245: 1246: id = srcfile->toChars(); 1247: len = strlen(id); 1248: dtsize_t(&dt, len); 1249: dtabytes(&dt,TYnptr, 0, len + 1, id); 1250: 1251: sfilename = symbol_generate(SCstatic,type_fake(TYdarray)); 1252: sfilename->Sdt = dt; 1253: sfilename->Sfl = FLdata; 1254: #if ELFOBJ 1255: sfilename->Sseg = CDATA; 1256: #endif 1257: #if MACHOBJ 1258: // Because of PIC and CDATA being in the _TEXT segment, cannot 1259: // have pointers in CDATA 1260: sfilename->Sseg = DATA; 1261: #endif 1262: outdata(sfilename); 1263: } 1264: 1265: efilename = el_var(sfilename); 1266: return efilename; 1267: } 1268: 1269: 1270: