void TypedefDeclaration::toObjFile(int multiobj) { //printf("TypedefDeclaration::toObjFile('%s')\n", toChars()); if (type->ty == Terror) { error("had semantic errors when compiling"); return; } if (global.params.symdebug) toDebug(this); type->genTypeInfo(NULL); TypeTypedef *tc = (TypeTypedef *)type; if (type->isZeroInit() || !tc->sym->init) ; else { enum_SC scclass = SCglobal; if (isInstantiated()) scclass = SCcomdat; // Generate static initializer toInitializer(); sinit->Sclass = scclass; sinit->Sfl = FLdata; sinit->Sdt = Initializer_toDt(tc->sym->init); out_readonly(sinit); outdata(sinit); } }
void initializerToDt(VarDeclaration *vd, DtBuilder& dtb) { Initializer_toDt(vd->_init, &dtb); // Look for static array that is block initialized ExpInitializer *ie = vd->_init->isExpInitializer(); Type *tb = vd->type->toBasetype(); if (tb->ty == Tsarray && ie && !tb->nextOf()->equals(ie->exp->type->toBasetype()->nextOf()) && ie->exp->implicitConvTo(tb->nextOf()) ) { size_t dim = ((TypeSArray *)tb)->dim->toInteger(); // Duplicate Sdt 'dim-1' times, as we already have the first one while (--dim > 0) { Expression_toDt(ie->exp, &dtb); } } }
void visit(VarDeclaration *vd) { //printf("VarDeclaration::toObjFile(%p '%s' type=%s) protection %d\n", vd, vd->toChars(), vd->type->toChars(), vd->protection); //printf("\talign = %d\n", vd->alignment); if (vd->type->ty == Terror) { vd->error("had semantic errors when compiling"); return; } if (vd->aliassym) { visitNoMultiObj(vd->toAlias()); return; } // Do not store variables we cannot take the address of if (!vd->canTakeAddressOf()) { return; } if (!vd->isDataseg() || vd->storage_class & STCextern) return; Symbol *s = toSymbol(vd); unsigned sz = vd->type->size(); Dsymbol *parent = vd->toParent(); s->Sclass = SCglobal; do { /* Global template data members need to be in comdat's * in case multiple .obj files instantiate the same * template with the same types. */ if (parent->isTemplateInstance() && !parent->isTemplateMixin()) { s->Sclass = SCcomdat; break; } parent = parent->parent; } while (parent); s->Sfl = FLdata; if (vd->init) { s->Sdt = Initializer_toDt(vd->init); // Look for static array that is block initialized ExpInitializer *ie = vd->init->isExpInitializer(); Type *tb = vd->type->toBasetype(); if (tb->ty == Tsarray && ie && !tb->nextOf()->equals(ie->exp->type->toBasetype()->nextOf()) && ie->exp->implicitConvTo(tb->nextOf()) ) { size_t dim = ((TypeSArray *)tb)->dim->toInteger(); // Duplicate Sdt 'dim-1' times, as we already have the first one dt_t **pdt = &s->Sdt; while (--dim > 0) { pdt = Expression_toDt(ie->exp, pdt); } } } else { Type_toDt(vd->type, &s->Sdt); } dt_optimize(s->Sdt); // See if we can convert a comdat to a comdef, // which saves on exe file space. if (s->Sclass == SCcomdat && s->Sdt && dtallzeros(s->Sdt) && !vd->isThreadlocal()) { s->Sclass = SCglobal; dt2common(&s->Sdt); } if (!sz && vd->type->toBasetype()->ty != Tsarray) assert(0); // this shouldn't be possible if (sz || objmod->allowZeroSize()) { outdata(s); if (vd->isExport()) objmod->export_symbol(s, 0); } }