comparison gen/classes.cpp @ 705:5a2983f97498

Fixed weird struct problem from downs, see mini/compile_structs1.d Rewrote DtoIndexStruct/Class , the old implementation were way too complex for what we really need now - since the DotVar changes.
author Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
date Tue, 14 Oct 2008 15:35:49 +0200
parents 92ec7487a1a0
children 635f91212b78
comparison
equal deleted inserted replaced
704:43165a082535 705:5a2983f97498
1092 result.push_back(r); 1092 result.push_back(r);
1093 } 1093 }
1094 1094
1095 ////////////////////////////////////////////////////////////////////////////////////////// 1095 //////////////////////////////////////////////////////////////////////////////////////////
1096 1096
1097 LLValue* DtoIndexClass(LLValue* ptr, ClassDeclaration* cd, Type* t, unsigned os, DStructIndexVector& idxs) 1097 LLValue* DtoIndexClass(LLValue* src, ClassDeclaration* cd, VarDeclaration* vd)
1098 { 1098 {
1099 Logger::println("checking for offset %u type %s:", os, t->toChars()); 1099 Logger::println("indexing class field %s:", vd->toPrettyChars());
1100 LOG_SCOPE; 1100 LOG_SCOPE;
1101 1101
1102 if (idxs.empty()) 1102 if (Logger::enabled())
1103 idxs.push_back(0); 1103 Logger::cout() << "src: " << *src << '\n';
1104
1105 // vd must be a field
1106 IrField* field = vd->ir.irField;
1107 assert(field);
1108
1109 unsigned idx = field->index + 2; // vtbl & monitor
1110 unsigned off = field->indexOffset;
1104 1111
1105 const LLType* st = DtoType(cd->type); 1112 const LLType* st = DtoType(cd->type);
1106 if (ptr->getType() != st) { 1113 src = DtoBitCast(src, st);
1107 ptr = gIR->ir->CreateBitCast(ptr, st, "tmp"); 1114
1108 } 1115 LLValue* val = DtoGEPi(src, 0,idx);
1109 1116 val = DtoBitCast(val, getPtrToType(DtoType(vd->type)));
1110 const LLType* llt = getPtrToType(DtoType(t)); 1117
1111 unsigned dataoffset = 2; 1118 if (off)
1112 1119 val = DtoGEPi1(val, off);
1113 IrStruct* irstruct = cd->ir.irStruct; 1120
1114 for (IrStruct::OffsetMap::iterator i=irstruct->offsets.begin(); i!=irstruct->offsets.end(); ++i) { 1121 if (Logger::enabled())
1115 VarDeclaration* vd = i->second.var; 1122 Logger::cout() << "value: " << *val << '\n';
1116 assert(vd); 1123
1117 Type* vdtype = vd->type->toBasetype(); 1124 return val;
1118 //Logger::println("found %u type %s", vd->offset, vdtype->toChars());
1119 assert(vd->ir.irField->index >= 0);
1120 if (os == vd->offset && vdtype->toBasetype() == t->toBasetype()) {
1121 Logger::println("found %s %s", vdtype->toChars(), vd->toChars());
1122 idxs.push_back(vd->ir.irField->index + dataoffset);
1123 //Logger::cout() << "indexing: " << *ptr << '\n';
1124 ptr = DtoGEPi(ptr, idxs, "tmp");
1125 if (ptr->getType() != llt)
1126 ptr = gIR->ir->CreateBitCast(ptr, llt, "tmp");
1127 //Logger::cout() << "indexing: " << *ptr << '\n';
1128 if (vd->ir.irField->indexOffset)
1129 ptr = llvm::GetElementPtrInst::Create(ptr, DtoConstUint(vd->ir.irField->indexOffset), "tmp", gIR->scopebb());
1130 //Logger::cout() << "indexing: " << *ptr << '\n';
1131 return ptr;
1132 }
1133 else if (vdtype->ty == Tstruct && (vd->offset + vdtype->size()) > os) {
1134 TypeStruct* ts = (TypeStruct*)vdtype;
1135 StructDeclaration* ssd = ts->sym;
1136 idxs.push_back(vd->ir.irField->index + dataoffset);
1137 if (vd->ir.irField->indexOffset) {
1138 Logger::println("has union field offset");
1139 ptr = DtoGEPi(ptr, idxs, "tmp");
1140 if (ptr->getType() != llt)
1141 ptr = gIR->ir->CreateBitCast(ptr, llt, "tmp");
1142 ptr = llvm::GetElementPtrInst::Create(ptr, DtoConstUint(vd->ir.irField->indexOffset), "tmp", gIR->scopebb());
1143 DStructIndexVector tmp;
1144 return DtoIndexStruct(ptr, ssd, t, os-vd->offset, tmp);
1145 }
1146 else {
1147 const LLType* sty = getPtrToType(DtoType(vd->type));
1148 if (ptr->getType() != sty) {
1149 ptr = gIR->ir->CreateBitCast(ptr, sty, "tmp");
1150 DStructIndexVector tmp;
1151 return DtoIndexStruct(ptr, ssd, t, os-vd->offset, tmp);
1152 }
1153 else {
1154 return DtoIndexStruct(ptr, ssd, t, os-vd->offset, idxs);
1155 }
1156 }
1157 }
1158 }
1159
1160 assert(0);
1161
1162 size_t llt_sz = getABITypeSize(llt->getContainedType(0));
1163 assert(os % llt_sz == 0);
1164 ptr = gIR->ir->CreateBitCast(ptr, llt, "tmp");
1165 return llvm::GetElementPtrInst::Create(ptr, DtoConstUint(os / llt_sz), "tmp", gIR->scopebb());
1166 } 1125 }
1167 1126
1168 ////////////////////////////////////////////////////////////////////////////////////////// 1127 //////////////////////////////////////////////////////////////////////////////////////////
1169 1128
1170 LLValue* DtoVirtualFunctionPointer(DValue* inst, FuncDeclaration* fdecl) 1129 LLValue* DtoVirtualFunctionPointer(DValue* inst, FuncDeclaration* fdecl)