comparison gen/toir.c @ 40:8b0e809563df trunk

[svn r44] Lots of bug fixes. New array literal support New array ~= operator support (for single element) New with statement support More...
author lindquist
date Fri, 19 Oct 2007 07:43:21 +0200
parents 77cdca8c210f
children 0b9b286b67b6
comparison
equal deleted inserted replaced
39:fd5e8bbfcb25 40:8b0e809563df
10 #include <math.h> 10 #include <math.h>
11 #include <sstream> 11 #include <sstream>
12 #include <fstream> 12 #include <fstream>
13 #include <iostream> 13 #include <iostream>
14 14
15 #include "llvm/Type.h" 15 #include "gen/llvm.h"
16 #include "llvm/DerivedTypes.h"
17 #include "llvm/Constants.h"
18 #include "llvm/Instructions.h"
19 #include "llvm/IntrinsicInst.h"
20 #include "llvm/CallingConv.h"
21 16
22 #include "total.h" 17 #include "total.h"
23 #include "init.h" 18 #include "init.h"
24 #include "symbol.h" 19 #include "symbol.h"
25 #include "mtype.h" 20 #include "mtype.h"
58 llvm::AllocaInst* allocainst = new llvm::AllocaInst(lltype, vd->toChars(), p->topallocapoint()); 53 llvm::AllocaInst* allocainst = new llvm::AllocaInst(lltype, vd->toChars(), p->topallocapoint());
59 //allocainst->setAlignment(vd->type->alignsize()); // TODO 54 //allocainst->setAlignment(vd->type->alignsize()); // TODO
60 vd->llvmValue = allocainst; 55 vd->llvmValue = allocainst;
61 // e->val = really needed?? 56 // e->val = really needed??
62 57
63 LLVM_DtoInitializer(vd->type, vd->init); 58 LLVM_DtoInitializer(vd->init);
64 } 59 }
65 } 60 }
66 // struct declaration 61 // struct declaration
67 else if (StructDeclaration* s = declaration->isStructDeclaration()) 62 else if (StructDeclaration* s = declaration->isStructDeclaration())
68 { 63 {
69 Logger::println("StructDeclaration"); 64 Logger::println("StructDeclaration");
70 s->toObjFile(); 65 s->toObjFile();
71 } 66 }
67 // function declaration
68 else if (FuncDeclaration* f = declaration->isFuncDeclaration())
69 {
70 Logger::println("FuncDeclaration");
71 f->toObjFile();
72 }
73 // alias declaration
74 else if (AliasDeclaration* a = declaration->isAliasDeclaration())
75 {
76 Logger::println("AliasDeclaration");
77 }
72 // unsupported declaration 78 // unsupported declaration
73 else 79 else
74 { 80 {
75 error("Only Var/Struct-Declaration is supported for DeclarationExp"); 81 error("Only Var/Struct-Declaration is supported for DeclarationExp");
76 fatal(); 82 fatal();
89 95
90 assert(var); 96 assert(var);
91 if (VarDeclaration* vd = var->isVarDeclaration()) 97 if (VarDeclaration* vd = var->isVarDeclaration())
92 { 98 {
93 Logger::println("VarDeclaration"); 99 Logger::println("VarDeclaration");
100
101 // needed to take care of forward references of global variables
102 if (!vd->llvmTouched && vd->isDataseg())
103 vd->toObjFile();
94 104
95 if (TypeInfoDeclaration* tid = vd->isTypeInfoDeclaration()) 105 if (TypeInfoDeclaration* tid = vd->isTypeInfoDeclaration())
96 { 106 {
97 Logger::println("TypeInfoDeclaration"); 107 Logger::println("TypeInfoDeclaration");
98 } 108 }
99 109
100 // this must be a dollar expression or some other magic value 110 // this must be a dollar expression or some other magic value
111 // or it could be a forward declaration of a global variable
101 if (!vd->llvmValue) 112 if (!vd->llvmValue)
102 { 113 {
103 // dollar 114 // dollar
104 if (!p->arrays.empty()) 115 if (!p->arrays.empty())
105 { 116 {
107 //llvm::Value* tmp = new llvm::GetElementPtrInst(p->arrays.back(),zero,zero,"tmp",p->scopebb()); 118 //llvm::Value* tmp = new llvm::GetElementPtrInst(p->arrays.back(),zero,zero,"tmp",p->scopebb());
108 llvm::Value* tmp = LLVM_DtoGEP(p->arrays.back(),zero,zero,"tmp",p->scopebb()); 119 llvm::Value* tmp = LLVM_DtoGEP(p->arrays.back(),zero,zero,"tmp",p->scopebb());
109 e->val = new llvm::LoadInst(tmp,"tmp",p->scopebb()); 120 e->val = new llvm::LoadInst(tmp,"tmp",p->scopebb());
110 e->type = elem::VAL; 121 e->type = elem::VAL;
111 } 122 }
112 // magic 123 // typeinfo
113 else 124 else if (TypeInfoDeclaration* tid = vd->isTypeInfoDeclaration())
114 { 125 {
115 if (TypeInfoDeclaration* tid = vd->isTypeInfoDeclaration()) 126 tid->toObjFile();
116 { 127 e->mem = tid->llvmValue;
117 tid->toObjFile(); 128 e->type = elem::VAR;
118 e->mem = tid->llvmValue; 129 }
119 e->type = elem::VAR; 130 // global forward ref
120 } 131 else {
121 else { 132 Logger::println("unsupported: %s\n", vd->toChars());
122 Logger::println("unsupported: %s\n", vd->toChars()); 133 assert(0 && "only magic supported is typeinfo");
123 assert(0 && "only magic supported is typeinfo");
124 }
125 } 134 }
126 return e; 135 return e;
127 } 136 }
128 137
129 // function parameter 138 // function parameter
132 if (vd->storage_class & (STCref | STCout)) { 141 if (vd->storage_class & (STCref | STCout)) {
133 e->mem = vd->llvmValue; 142 e->mem = vd->llvmValue;
134 e->type = elem::VAR; 143 e->type = elem::VAR;
135 } 144 }
136 else { 145 else {
137 if (vd->type->ty == Tstruct || vd->type->ty == Tdelegate || vd->type->ty == Tarray) { 146 if (LLVM_DtoIsPassedByRef(vd->type)) {
138 e->mem = vd->llvmValue; 147 e->mem = vd->llvmValue;
139 e->type = elem::VAR; 148 e->type = elem::VAR;
140 } 149 }
141 else { 150 else {
142 if (llvm::isa<llvm::Argument>(vd->llvmValue)) { 151 if (llvm::isa<llvm::Argument>(vd->llvmValue)) {
171 e->funcdecl = fdecl; 180 e->funcdecl = fdecl;
172 } 181 }
173 else if (SymbolDeclaration* sdecl = var->isSymbolDeclaration()) 182 else if (SymbolDeclaration* sdecl = var->isSymbolDeclaration())
174 { 183 {
175 // this seems to be the static initialiser for structs 184 // this seems to be the static initialiser for structs
176 Logger::print("Sym: type=%s\n", sdecl->type->toChars()); 185 Type* sdecltype = LLVM_DtoDType(sdecl->type);
177 assert(sdecl->type->ty == Tstruct); 186 Logger::print("Sym: type=%s\n", sdecltype->toChars());
178 //assert(sdecl->llvmInitZ); 187 assert(sdecltype->ty == Tstruct);
179 //e->val = sdecl->llvmInitZ; 188 TypeStruct* ts = (TypeStruct*)sdecltype;
180 TypeStruct* ts = (TypeStruct*)sdecl->type;
181 e->mem = ts->llvmInit; 189 e->mem = ts->llvmInit;
182 assert(e->mem); 190 assert(e->mem);
183 e->type = elem::VAR; 191 e->type = elem::VAR;
184 } 192 }
185 else 193 else
191 return e; 199 return e;
192 } 200 }
193 201
194 ////////////////////////////////////////////////////////////////////////////////////////// 202 //////////////////////////////////////////////////////////////////////////////////////////
195 203
204 llvm::Constant* VarExp::toConstElem(IRState* p)
205 {
206 Logger::print("VarExp::toConstElem: %s | %s\n", toChars(), type->toChars());
207 LOG_SCOPE;
208 if (SymbolDeclaration* sdecl = var->isSymbolDeclaration())
209 {
210 // this seems to be the static initialiser for structs
211 Type* sdecltype = LLVM_DtoDType(sdecl->type);
212 Logger::print("Sym: type=%s\n", sdecltype->toChars());
213 assert(sdecltype->ty == Tstruct);
214 TypeStruct* ts = (TypeStruct*)sdecltype;
215 assert(ts->sym->llvmInitZ);
216 return ts->sym->llvmInitZ;
217 }
218 assert(0 && "Only support const var exp is SymbolDeclaration");
219 return NULL;
220 }
221
222 //////////////////////////////////////////////////////////////////////////////////////////
223
196 elem* IntegerExp::toElem(IRState* p) 224 elem* IntegerExp::toElem(IRState* p)
197 { 225 {
198 Logger::print("IntegerExp::toElem: %s | %s\n", toChars(), type->toChars()); 226 Logger::print("IntegerExp::toElem: %s | %s\n", toChars(), type->toChars());
199 LOG_SCOPE; 227 LOG_SCOPE;
200 elem* e = new elem; 228 elem* e = new elem;
229 e->val = toConstElem(p);
230 e->type = elem::CONST;
231 return e;
232 }
233
234 //////////////////////////////////////////////////////////////////////////////////////////
235
236 llvm::Constant* IntegerExp::toConstElem(IRState* p)
237 {
238 Logger::print("IntegerExp::toConstElem: %s | %s\n", toChars(), type->toChars());
239 LOG_SCOPE;
201 const llvm::Type* t = LLVM_DtoType(type); 240 const llvm::Type* t = LLVM_DtoType(type);
202 if (llvm::isa<llvm::PointerType>(t)) { 241 if (llvm::isa<llvm::PointerType>(t)) {
203 llvm::Constant* i = llvm::ConstantInt::get(LLVM_DtoSize_t(),(uint64_t)value,false); 242 llvm::Constant* i = llvm::ConstantInt::get(LLVM_DtoSize_t(),(uint64_t)value,false);
204 e->val = llvm::ConstantExpr::getIntToPtr(i, t); 243 return llvm::ConstantExpr::getIntToPtr(i, t);
205 } 244 }
206 else if (llvm::isa<llvm::IntegerType>(t)) { 245 else if (llvm::isa<llvm::IntegerType>(t)) {
207 e->val = llvm::ConstantInt::get(t,(uint64_t)value,!type->isunsigned()); 246 return llvm::ConstantInt::get(t,(uint64_t)value,!type->isunsigned());
208 } 247 }
209 else { 248 assert(0);
210 assert(0); 249 return NULL;
211 } 250 }
251
252 //////////////////////////////////////////////////////////////////////////////////////////
253
254 elem* RealExp::toElem(IRState* p)
255 {
256 Logger::print("RealExp::toElem: %s | %s\n", toChars(), type->toChars());
257 LOG_SCOPE;
258 elem* e = new elem;
259 e->val = toConstElem(p);
212 e->type = elem::CONST; 260 e->type = elem::CONST;
213 return e; 261 return e;
214 } 262 }
215 263
216 ////////////////////////////////////////////////////////////////////////////////////////// 264 //////////////////////////////////////////////////////////////////////////////////////////
217 265
218 elem* RealExp::toElem(IRState* p) 266 llvm::Constant* RealExp::toConstElem(IRState* p)
219 { 267 {
220 Logger::print("RealExp::toElem: %s | %s\n", toChars(), type->toChars()); 268 Logger::print("RealExp::toConstElem: %s | %s\n", toChars(), type->toChars());
221 LOG_SCOPE; 269 LOG_SCOPE;
222 elem* e = new elem;
223 const llvm::Type* fty = LLVM_DtoType(type); 270 const llvm::Type* fty = LLVM_DtoType(type);
224 if (type->ty == Tfloat32) 271 if (type->ty == Tfloat32)
225 e->val = llvm::ConstantFP::get(fty,float(value)); 272 return llvm::ConstantFP::get(fty,float(value));
226 else if (type->ty == Tfloat64 || type->ty == Tfloat80) 273 else if (type->ty == Tfloat64 || type->ty == Tfloat80)
227 e->val = llvm::ConstantFP::get(fty,double(value)); 274 return llvm::ConstantFP::get(fty,double(value));
228 else 275 assert(0);
229 assert(0); 276 return NULL;
230 e->type = elem::CONST;
231 return e;
232 } 277 }
233 278
234 ////////////////////////////////////////////////////////////////////////////////////////// 279 //////////////////////////////////////////////////////////////////////////////////////////
235 280
236 elem* NullExp::toElem(IRState* p) 281 elem* NullExp::toElem(IRState* p)
237 { 282 {
238 Logger::print("NullExp::toElem(type=%s): %s\n", type->toChars(),toChars()); 283 Logger::print("NullExp::toElem(type=%s): %s\n", type->toChars(),toChars());
239 LOG_SCOPE; 284 LOG_SCOPE;
240 elem* e = new elem; 285 elem* e = new elem;
286 e->val = toConstElem(p);
287 e->type = elem::NUL;
288 //Logger::cout() << "null value is now " << *e->val << '\n';
289 return e;
290 }
291
292 //////////////////////////////////////////////////////////////////////////////////////////
293
294 llvm::Constant* NullExp::toConstElem(IRState* p)
295 {
296 Logger::print("NullExp::toConstElem(type=%s): %s\n", type->toChars(),toChars());
297 LOG_SCOPE;
241 const llvm::Type* t = LLVM_DtoType(type); 298 const llvm::Type* t = LLVM_DtoType(type);
242
243 if (type->ty == Tarray) { 299 if (type->ty == Tarray) {
244 assert(llvm::isa<llvm::StructType>(t)); 300 assert(llvm::isa<llvm::StructType>(t));
245 e->val = llvm::ConstantAggregateZero::get(t); 301 return llvm::ConstantAggregateZero::get(t);
246 } 302 }
247 else 303 else {
248 e->val = llvm::Constant::getNullValue(t); 304 return llvm::Constant::getNullValue(t);
249 assert(e->val); 305 }
250 306 assert(0);
251 Logger::cout() << "null value is now " << *e->val << '\n'; 307 return NULL;
252 e->type = elem::NUL;
253 return e;
254 } 308 }
255 309
256 ////////////////////////////////////////////////////////////////////////////////////////// 310 //////////////////////////////////////////////////////////////////////////////////////////
257 311
258 elem* StringExp::toElem(IRState* p) 312 elem* StringExp::toElem(IRState* p)
259 { 313 {
260 Logger::print("StringExp::toElem: %s | \n", toChars(), type->toChars()); 314 Logger::print("StringExp::toElem: %s | \n", toChars(), type->toChars());
261 LOG_SCOPE; 315 LOG_SCOPE;
262 316
263 assert(type->next->ty == Tchar && "Only char is supported"); 317 Type* dtype = LLVM_DtoDType(type);
318
319 assert(dtype->next->ty == Tchar && "Only char is supported");
264 assert(sz == 1); 320 assert(sz == 1);
265 321
266 const llvm::Type* ct = LLVM_DtoType(type->next); 322 const llvm::Type* ct = LLVM_DtoType(dtype->next);
267 //printf("ct = %s\n", type->next->toChars()); 323 //printf("ct = %s\n", type->next->toChars());
268 const llvm::ArrayType* at = llvm::ArrayType::get(ct,len+1); 324 const llvm::ArrayType* at = llvm::ArrayType::get(ct,len+1);
269 325
270 uint8_t* str = (uint8_t*)string; 326 uint8_t* str = (uint8_t*)string;
271 std::string cont((char*)str, len); 327 std::string cont((char*)str, len);
274 330
275 llvm::GlobalValue::LinkageTypes _linkage = llvm::GlobalValue::InternalLinkage;//WeakLinkage; 331 llvm::GlobalValue::LinkageTypes _linkage = llvm::GlobalValue::InternalLinkage;//WeakLinkage;
276 llvm::GlobalVariable* gvar = new llvm::GlobalVariable(at,true,_linkage,_init,"stringliteral",gIR->module); 332 llvm::GlobalVariable* gvar = new llvm::GlobalVariable(at,true,_linkage,_init,"stringliteral",gIR->module);
277 333
278 llvm::ConstantInt* zero = llvm::ConstantInt::get(llvm::Type::Int32Ty, 0, false); 334 llvm::ConstantInt* zero = llvm::ConstantInt::get(llvm::Type::Int32Ty, 0, false);
279 //llvm::Value* arrptr = LLVM_DtoGEP(gvar,zero,zero,"tmp",p->scopebb());
280 llvm::Constant* idxs[2] = { zero, zero }; 335 llvm::Constant* idxs[2] = { zero, zero };
281 llvm::Constant* arrptr = llvm::ConstantExpr::getGetElementPtr(gvar,idxs,2); 336 llvm::Constant* arrptr = llvm::ConstantExpr::getGetElementPtr(gvar,idxs,2);
282 337
283 elem* e = new elem; 338 elem* e = new elem;
284 339
285 if (type->ty == Tarray) { 340 if (dtype->ty == Tarray) {
286 llvm::Constant* clen = llvm::ConstantInt::get(LLVM_DtoSize_t(),len,false); 341 llvm::Constant* clen = llvm::ConstantInt::get(LLVM_DtoSize_t(),len,false);
287 if (p->lvals.empty()) { 342 if (p->lvals.empty() || !p->toplval()) {
288 e->type = elem::SLICE; 343 e->type = elem::SLICE;
289 e->arg = clen; 344 e->arg = clen;
290 e->mem = arrptr; 345 e->mem = arrptr;
291 return e; 346 return e;
292 } 347 }
293 else { 348 else if (llvm::Value* arr = p->toplval()) {
294 llvm::Value* arr = p->toplval();
295 if (llvm::isa<llvm::GlobalVariable>(arr)) { 349 if (llvm::isa<llvm::GlobalVariable>(arr)) {
296 e->val = LLVM_DtoConstantSlice(clen, arrptr); 350 e->val = LLVM_DtoConstantSlice(clen, arrptr);
297 } 351 }
298 else { 352 else {
299 LLVM_DtoSetArray(arr, clen, arrptr); 353 LLVM_DtoSetArray(arr, clen, arrptr);
300 e->inplace = true; 354 e->inplace = true;
301 } 355 }
302 } 356 }
303 } 357 else
304 else if (type->ty == Tsarray) { 358 assert(0);
359 }
360 else if (dtype->ty == Tsarray) {
305 const llvm::Type* dstType = llvm::PointerType::get(llvm::ArrayType::get(ct, len)); 361 const llvm::Type* dstType = llvm::PointerType::get(llvm::ArrayType::get(ct, len));
306 e->mem = new llvm::BitCastInst(gvar, dstType, "tmp", gIR->scopebb()); 362 e->mem = new llvm::BitCastInst(gvar, dstType, "tmp", gIR->scopebb());
307 } 363 }
308 else if (type->ty == Tpointer) { 364 else if (dtype->ty == Tpointer) {
309 e->mem = arrptr; 365 e->mem = arrptr;
310 } 366 }
311 else { 367 else {
312 assert(0); 368 assert(0);
313 } 369 }
314 370
315 e->type = elem::VAL; 371 e->type = elem::VAL;
316 372
317 return e; 373 return e;
374 }
375
376 //////////////////////////////////////////////////////////////////////////////////////////
377
378 llvm::Constant* StringExp::toConstElem(IRState* p)
379 {
380 Logger::print("StringExp::toConstElem: %s | %s\n", toChars(), type->toChars());
381 LOG_SCOPE;
382
383 uint8_t* str = (uint8_t*)string;
384 std::string cont((char*)str, len);
385
386 Type* t = LLVM_DtoDType(type);
387
388 llvm::Constant* _init = llvm::ConstantArray::get(cont,true);
389 if (t->ty == Tsarray) {
390 return _init;
391 }
392 llvm::GlobalValue::LinkageTypes _linkage = llvm::GlobalValue::InternalLinkage;//WeakLinkage;
393 llvm::GlobalVariable* gvar = new llvm::GlobalVariable(_init->getType(),true,_linkage,_init,"stringliteral",gIR->module);
394
395 llvm::ConstantInt* zero = llvm::ConstantInt::get(llvm::Type::Int32Ty, 0, false);
396 llvm::Constant* idxs[2] = { zero, zero };
397 llvm::Constant* arrptr = llvm::ConstantExpr::getGetElementPtr(gvar,idxs,2);
398
399 if (t->ty == Tpointer) {
400 return arrptr;
401 }
402
403 if (t->ty == Tarray) {
404 llvm::Constant* clen = llvm::ConstantInt::get(LLVM_DtoSize_t(),len,false);
405 return LLVM_DtoConstantSlice(clen, arrptr);
406 }
407
408 assert(0);
409 return NULL;
318 } 410 }
319 411
320 ////////////////////////////////////////////////////////////////////////////////////////// 412 //////////////////////////////////////////////////////////////////////////////////////////
321 413
322 elem* AssignExp::toElem(IRState* p) 414 elem* AssignExp::toElem(IRState* p)
351 assert(0); 443 assert(0);
352 } 444 }
353 } 445 }
354 //e->val = l->store(r->getValue()); 446 //e->val = l->store(r->getValue());
355 447
356 TY e1ty = e1->type->ty; 448 Type* e1type = LLVM_DtoDType(e1->type);
357 TY e2ty = e2->type->ty; 449 Type* e2type = LLVM_DtoDType(e2->type);
358 450 TY e1ty = e1type->ty;
359 elem* e = new elem; 451 TY e2ty = e2type->ty;
452
453 elem* e = new elem;
454 e->type = elem::VAR;
360 455
361 // struct 456 // struct
362 if (e1ty == Tstruct) { 457 if (e1ty == Tstruct) {
458 e->mem = l->mem;
363 // struct + struct 459 // struct + struct
364 if (e2ty == Tstruct) { 460 if (e2ty == Tstruct) {
365 // struct literals do the assignment themselvs (in place) 461 // struct literals do the assignment themselvs (in place)
366 if (!r->inplace) { 462 if (!r->inplace) {
367 TypeStruct* ts = (TypeStruct*)e2->type; 463 TypeStruct* ts = (TypeStruct*)e2type;
368 assert(r->mem); 464 LLVM_DtoStructCopy(ts,l->mem,r->getValue());
369 LLVM_DtoStructCopy(ts,l->mem,r->mem);
370 } 465 }
371 else { 466 else {
372 e->inplace = true; 467 e->inplace = true;
373 } 468 }
374 } 469 }
375 // struct + const int 470 // struct + const int
376 else if (e2->type->isintegral()){ 471 else if (e2type->isintegral()){
377 IntegerExp* iexp = (IntegerExp*)e2; 472 IntegerExp* iexp = (IntegerExp*)e2;
378 assert(iexp->value == 0 && "Only integral struct initializer allowed is zero"); 473 assert(iexp->value == 0 && "Only integral struct initializer allowed is zero");
379 TypeStruct* st = (TypeStruct*)e1->type; 474 TypeStruct* st = (TypeStruct*)e1type;
380 LLVM_DtoStructZeroInit(st, l->mem); 475 LLVM_DtoStructZeroInit(st, l->mem);
381 } 476 }
382 // :x 477 // :x
383 else 478 else
384 assert(0 && "struct = unknown"); 479 assert(0 && "struct = unknown");
385 } 480 }
386 else if (e1ty == Tsarray) { 481 else if (e1ty == Tsarray) {
387 assert(0 && "static array = not supported"); 482 assert(0 && "static array not supported");
388 } 483 }
389 else if (e1ty == Tarray) { 484 else if (e1ty == Tarray) {
390 if (e2->type->isscalar() || e2->type->ty == Tclass){ 485 if (e2type->isscalar() || e2type->ty == Tclass){
391 LLVM_DtoArrayInit(l->mem, r->getValue()); 486 LLVM_DtoArrayInit(l->mem, r->getValue());
392 } 487 }
393 else if (e2ty == Tarray) { 488 else if (e2ty == Tarray) {
394 //new llvm::StoreInst(r->val,l->val,p->scopebb()); 489 //new llvm::StoreInst(r->val,l->val,p->scopebb());
395 if (r->type == elem::NUL) { 490 if (r->type == elem::NUL) {
396 llvm::Constant* c = llvm::cast<llvm::Constant>(r->val); 491 llvm::Constant* c = llvm::cast<llvm::Constant>(r->val);
397 assert(c->isNullValue()); 492 assert(c->isNullValue());
398 LLVM_DtoNullArray(l->mem); 493 LLVM_DtoNullArray(l->mem);
494 e->mem = l->mem;
399 } 495 }
400 else if (r->type == elem::SLICE) { 496 else if (r->type == elem::SLICE) {
401 if (l->type == elem::SLICE) 497 if (l->type == elem::SLICE) {
402 LLVM_DtoArrayCopy(l,r); 498 LLVM_DtoArrayCopy(l,r);
403 else 499 e->type = elem::SLICE;
404 LLVM_DtoSetArray(l->mem,r->arg,r->mem); 500 e->mem = l->mem;
501 e->arg = l->arg;
502 }
503 else {
504 LLVM_DtoSetArray(l->mem,r->arg,r->mem);
505 e->mem = l->mem;
506 }
405 } 507 }
406 else { 508 else {
407 // new expressions write directly to the array reference 509 // new expressions write directly to the array reference
408 // so do string literals 510 // so do string literals
511 e->mem = l->mem;
409 if (!r->inplace) { 512 if (!r->inplace) {
410 assert(r->mem); 513 assert(r->mem);
411 LLVM_DtoArrayAssign(l->mem, r->mem); 514 LLVM_DtoArrayAssign(l->mem, r->mem);
412 } 515 }
413 else { 516 else {
417 } 520 }
418 else 521 else
419 assert(0); 522 assert(0);
420 } 523 }
421 else if (e1ty == Tpointer) { 524 else if (e1ty == Tpointer) {
525 e->mem = l->mem;
422 if (e2ty == Tpointer) { 526 if (e2ty == Tpointer) {
423 llvm::Value* v = r->field ? r->mem : r->getValue(); 527 llvm::Value* v = r->field ? r->mem : r->getValue();
424 Logger::cout() << "*=*: " << *v << ", " << *l->mem << '\n'; 528 Logger::cout() << "*=*: " << *v << ", " << *l->mem << '\n';
425 new llvm::StoreInst(v, l->mem, p->scopebb()); 529 new llvm::StoreInst(v, l->mem, p->scopebb());
426 } 530 }
431 if (e2ty == Tclass) { 535 if (e2ty == Tclass) {
432 llvm::Value* tmp = r->getValue(); 536 llvm::Value* tmp = r->getValue();
433 Logger::cout() << "tmp: " << *tmp << " ||| " << *l->mem << '\n'; 537 Logger::cout() << "tmp: " << *tmp << " ||| " << *l->mem << '\n';
434 // assignment to this in constructor special case 538 // assignment to this in constructor special case
435 if (l->isthis) { 539 if (l->isthis) {
436 FuncDeclaration* fdecl = p->funcdecls.back(); 540 FuncDeclaration* fdecl = p->func().decl;
437 // respecify the this param 541 // respecify the this param
438 if (!llvm::isa<llvm::AllocaInst>(fdecl->llvmThisVar)) 542 if (!llvm::isa<llvm::AllocaInst>(fdecl->llvmThisVar))
439 fdecl->llvmThisVar = new llvm::AllocaInst(tmp->getType(), "newthis", p->topallocapoint()); 543 fdecl->llvmThisVar = new llvm::AllocaInst(tmp->getType(), "newthis", p->topallocapoint());
440 new llvm::StoreInst(tmp, fdecl->llvmThisVar, p->scopebb()); 544 new llvm::StoreInst(tmp, fdecl->llvmThisVar, p->scopebb());
545 e->mem = fdecl->llvmThisVar;
441 } 546 }
442 // regular class ref -> class ref assignment 547 // regular class ref -> class ref assignment
443 else { 548 else {
444 new llvm::StoreInst(tmp, l->mem, p->scopebb()); 549 new llvm::StoreInst(tmp, l->mem, p->scopebb());
550 e->mem = l->mem;
445 } 551 }
446 } 552 }
447 else 553 else
448 assert(0); 554 assert(0);
449 } 555 }
452 if (e2ty == Tdelegate) { 558 if (e2ty == Tdelegate) {
453 if (r->type == elem::NUL) { 559 if (r->type == elem::NUL) {
454 llvm::Constant* c = llvm::cast<llvm::Constant>(r->val); 560 llvm::Constant* c = llvm::cast<llvm::Constant>(r->val);
455 if (c->isNullValue()) { 561 if (c->isNullValue()) {
456 LLVM_DtoNullDelegate(l->mem); 562 LLVM_DtoNullDelegate(l->mem);
563 e->mem = l->mem;
457 } 564 }
458 else 565 else
459 assert(0); 566 assert(0);
460 } 567 }
461 else if (r->inplace) { 568 else if (r->inplace) {
462 // do nothing 569 // do nothing
463 e->inplace = true; 570 e->inplace = true;
571 e->mem = l->mem;
464 } 572 }
465 else 573 else
466 assert(0); 574 assert(0);
467 } 575 }
468 else 576 else
470 } 578 }
471 // !struct && !array && !pointer && !class 579 // !struct && !array && !pointer && !class
472 else { 580 else {
473 Logger::cout() << *l->mem << '\n'; 581 Logger::cout() << *l->mem << '\n';
474 new llvm::StoreInst(r->getValue(),l->mem,p->scopebb()); 582 new llvm::StoreInst(r->getValue(),l->mem,p->scopebb());
583 e->mem = l->mem;
475 } 584 }
476 585
477 delete r; 586 delete r;
478 delete l; 587 delete l;
588
479 return e; 589 return e;
480 } 590 }
481 591
482 ////////////////////////////////////////////////////////////////////////////////////////// 592 //////////////////////////////////////////////////////////////////////////////////////////
483 593
487 LOG_SCOPE; 597 LOG_SCOPE;
488 elem* e = new elem; 598 elem* e = new elem;
489 elem* l = e1->toElem(p); 599 elem* l = e1->toElem(p);
490 elem* r = e2->toElem(p); 600 elem* r = e2->toElem(p);
491 601
492 if (e1->type != e2->type) { 602 Type* t = LLVM_DtoDType(type);
493 if (e1->type->ty == Tpointer && e1->type->next->ty == Tstruct) { 603 Type* e1type = LLVM_DtoDType(e1->type);
604 Type* e2type = LLVM_DtoDType(e2->type);
605
606 if (e1type != e2type) {
607 if (e1type->ty == Tpointer && e1type->next->ty == Tstruct) {
494 //assert(l->field); 608 //assert(l->field);
495 assert(r->type == elem::CONST); 609 assert(r->type == elem::CONST);
496 llvm::ConstantInt* cofs = llvm::cast<llvm::ConstantInt>(r->val); 610 llvm::ConstantInt* cofs = llvm::cast<llvm::ConstantInt>(r->val);
497 611
498 TypeStruct* ts = (TypeStruct*)e1->type->next; 612 TypeStruct* ts = (TypeStruct*)e1type->next;
499 std::vector<unsigned> offsets(1,0); 613 std::vector<unsigned> offsets(1,0);
500 ts->sym->offsetToIndex(type->next, cofs->getZExtValue(), offsets); 614 ts->sym->offsetToIndex(t->next, cofs->getZExtValue(), offsets);
501 e->mem = LLVM_DtoGEP(l->getValue(), offsets, "tmp", p->scopebb()); 615 e->mem = LLVM_DtoGEP(l->getValue(), offsets, "tmp", p->scopebb());
502 e->type = elem::VAR; 616 e->type = elem::VAR;
503 e->field = true; 617 e->field = true;
504 } 618 }
505 else if (e1->type->ty == Tpointer) { 619 else if (e1->type->ty == Tpointer) {
527 LOG_SCOPE; 641 LOG_SCOPE;
528 642
529 elem* l = e1->toElem(p); 643 elem* l = e1->toElem(p);
530 elem* r = e2->toElem(p); 644 elem* r = e2->toElem(p);
531 645
646 Type* e1type = LLVM_DtoDType(e1->type);
647
532 elem* e = new elem; 648 elem* e = new elem;
533 llvm::Value* val = 0; 649 llvm::Value* val = 0;
534 if (e1->type->ty == Tpointer) { 650 if (e1type->ty == Tpointer) {
535 val = e->mem = new llvm::GetElementPtrInst(l->getValue(),r->getValue(),"tmp",p->scopebb()); 651 val = e->mem = new llvm::GetElementPtrInst(l->getValue(),r->getValue(),"tmp",p->scopebb());
536 } 652 }
537 else { 653 else {
538 val = e->val = llvm::BinaryOperator::createAdd(l->getValue(),r->getValue(),"tmp",p->scopebb()); 654 val = e->val = llvm::BinaryOperator::createAdd(l->getValue(),r->getValue(),"tmp",p->scopebb());
539 } 655 }
596 LOG_SCOPE; 712 LOG_SCOPE;
597 713
598 elem* l = e1->toElem(p); 714 elem* l = e1->toElem(p);
599 elem* r = e2->toElem(p); 715 elem* r = e2->toElem(p);
600 716
717 Type* e1type = LLVM_DtoDType(e1->type);
718
601 llvm::Value* tmp = 0; 719 llvm::Value* tmp = 0;
602 if (e1->type->ty == Tpointer) { 720 if (e1type->ty == Tpointer) {
603 tmp = r->getValue(); 721 tmp = r->getValue();
604 llvm::Value* zero = llvm::ConstantInt::get(tmp->getType(),0,false); 722 llvm::Value* zero = llvm::ConstantInt::get(tmp->getType(),0,false);
605 tmp = llvm::BinaryOperator::createSub(zero,tmp,"tmp",p->scopebb()); 723 tmp = llvm::BinaryOperator::createSub(zero,tmp,"tmp",p->scopebb());
606 tmp = new llvm::GetElementPtrInst(l->getValue(),tmp,"tmp",p->scopebb()); 724 tmp = new llvm::GetElementPtrInst(l->getValue(),tmp,"tmp",p->scopebb());
607 } 725 }
688 LOG_SCOPE; 806 LOG_SCOPE;
689 elem* e = new elem; 807 elem* e = new elem;
690 elem* l = e1->toElem(p); 808 elem* l = e1->toElem(p);
691 elem* r = e2->toElem(p); 809 elem* r = e2->toElem(p);
692 810
693 if (type->isunsigned()) 811 Type* t = LLVM_DtoDType(type);
812
813 if (t->isunsigned())
694 e->val = llvm::BinaryOperator::createUDiv(l->getValue(),r->getValue(),"tmp",p->scopebb()); 814 e->val = llvm::BinaryOperator::createUDiv(l->getValue(),r->getValue(),"tmp",p->scopebb());
695 else if (type->isintegral()) 815 else if (t->isintegral())
696 e->val = llvm::BinaryOperator::createSDiv(l->getValue(),r->getValue(),"tmp",p->scopebb()); 816 e->val = llvm::BinaryOperator::createSDiv(l->getValue(),r->getValue(),"tmp",p->scopebb());
697 else if (type->isfloating()) 817 else if (t->isfloating())
698 e->val = llvm::BinaryOperator::createFDiv(l->getValue(),r->getValue(),"tmp",p->scopebb()); 818 e->val = llvm::BinaryOperator::createFDiv(l->getValue(),r->getValue(),"tmp",p->scopebb());
699 else 819 else
700 assert(0); 820 assert(0);
701 e->type = elem::VAL; 821 e->type = elem::VAL;
702 delete l; 822 delete l;
712 LOG_SCOPE; 832 LOG_SCOPE;
713 833
714 elem* l = e1->toElem(p); 834 elem* l = e1->toElem(p);
715 elem* r = e2->toElem(p); 835 elem* r = e2->toElem(p);
716 836
837 Type* t = LLVM_DtoDType(type);
838
717 llvm::Value* tmp; 839 llvm::Value* tmp;
718 if (type->isunsigned()) 840 if (t->isunsigned())
719 tmp = llvm::BinaryOperator::createUDiv(l->getValue(),r->getValue(),"tmp",p->scopebb()); 841 tmp = llvm::BinaryOperator::createUDiv(l->getValue(),r->getValue(),"tmp",p->scopebb());
720 else if (type->isintegral()) 842 else if (t->isintegral())
721 tmp = llvm::BinaryOperator::createSDiv(l->getValue(),r->getValue(),"tmp",p->scopebb()); 843 tmp = llvm::BinaryOperator::createSDiv(l->getValue(),r->getValue(),"tmp",p->scopebb());
722 else if (type->isfloating()) 844 else if (t->isfloating())
723 tmp = llvm::BinaryOperator::createFDiv(l->getValue(),r->getValue(),"tmp",p->scopebb()); 845 tmp = llvm::BinaryOperator::createFDiv(l->getValue(),r->getValue(),"tmp",p->scopebb());
724 else 846 else
725 assert(0); 847 assert(0);
726 848
727 /*llvm::Value* storeVal = l->storeVal ? l->storeVal : l->val; 849 /*llvm::Value* storeVal = l->storeVal ? l->storeVal : l->val;
751 LOG_SCOPE; 873 LOG_SCOPE;
752 elem* e = new elem; 874 elem* e = new elem;
753 elem* l = e1->toElem(p); 875 elem* l = e1->toElem(p);
754 elem* r = e2->toElem(p); 876 elem* r = e2->toElem(p);
755 877
756 if (type->isunsigned()) 878 Type* t = LLVM_DtoDType(type);
879
880 if (t->isunsigned())
757 e->val = llvm::BinaryOperator::createURem(l->getValue(),r->getValue(),"tmp",p->scopebb()); 881 e->val = llvm::BinaryOperator::createURem(l->getValue(),r->getValue(),"tmp",p->scopebb());
758 else if (type->isintegral()) 882 else if (t->isintegral())
759 e->val = llvm::BinaryOperator::createSRem(l->getValue(),r->getValue(),"tmp",p->scopebb()); 883 e->val = llvm::BinaryOperator::createSRem(l->getValue(),r->getValue(),"tmp",p->scopebb());
760 else if (type->isfloating()) 884 else if (t->isfloating())
761 e->val = llvm::BinaryOperator::createFRem(l->getValue(),r->getValue(),"tmp",p->scopebb()); 885 e->val = llvm::BinaryOperator::createFRem(l->getValue(),r->getValue(),"tmp",p->scopebb());
762 else 886 else
763 assert(0); 887 assert(0);
764 e->type = elem::VAL; 888 e->type = elem::VAL;
765 delete l; 889 delete l;
775 LOG_SCOPE; 899 LOG_SCOPE;
776 900
777 elem* l = e1->toElem(p); 901 elem* l = e1->toElem(p);
778 elem* r = e2->toElem(p); 902 elem* r = e2->toElem(p);
779 903
904 Type* t = LLVM_DtoDType(type);
905
780 llvm::Value* tmp; 906 llvm::Value* tmp;
781 if (type->isunsigned()) 907 if (t->isunsigned())
782 tmp = llvm::BinaryOperator::createURem(l->getValue(),r->getValue(),"tmp",p->scopebb()); 908 tmp = llvm::BinaryOperator::createURem(l->getValue(),r->getValue(),"tmp",p->scopebb());
783 else if (type->isintegral()) 909 else if (t->isintegral())
784 tmp = llvm::BinaryOperator::createSRem(l->getValue(),r->getValue(),"tmp",p->scopebb()); 910 tmp = llvm::BinaryOperator::createSRem(l->getValue(),r->getValue(),"tmp",p->scopebb());
785 else if (type->isfloating()) 911 else if (t->isfloating())
786 tmp = llvm::BinaryOperator::createFRem(l->getValue(),r->getValue(),"tmp",p->scopebb()); 912 tmp = llvm::BinaryOperator::createFRem(l->getValue(),r->getValue(),"tmp",p->scopebb());
787 else 913 else
788 assert(0); 914 assert(0);
789 915
790 /*llvm::Value* storeVal = l->storeVal ? l->storeVal : l->val; 916 /*llvm::Value* storeVal = l->storeVal ? l->storeVal : l->val;
823 // hidden struct return parameter handling 949 // hidden struct return parameter handling
824 bool retinptr = false; 950 bool retinptr = false;
825 951
826 TypeFunction* tf = 0; 952 TypeFunction* tf = 0;
827 953
954 Type* e1type = LLVM_DtoDType(e1->type);
955
828 // regular functions 956 // regular functions
829 if (e1->type->ty == Tfunction) { 957 if (e1type->ty == Tfunction) {
830 tf = (TypeFunction*)e1->type; 958 tf = (TypeFunction*)e1type;
831 if (tf->llvmRetInPtr) { 959 if (tf->llvmRetInPtr) {
832 retinptr = true; 960 retinptr = true;
833 } 961 }
834 dlink = tf->linkage; 962 dlink = tf->linkage;
835 } 963 }
836 964
837 // delegates 965 // delegates
838 else if (e1->type->ty == Tdelegate) { 966 else if (e1type->ty == Tdelegate) {
839 Logger::println("delegateTy = %s\n", e1->type->toChars()); 967 Logger::println("delegateTy = %s\n", e1type->toChars());
840 assert(e1->type->next->ty == Tfunction); 968 assert(e1type->next->ty == Tfunction);
841 tf = (TypeFunction*)e1->type->next; 969 tf = (TypeFunction*)e1type->next;
842 if (tf->llvmRetInPtr) { 970 if (tf->llvmRetInPtr) {
843 retinptr = true; 971 retinptr = true;
844 } 972 }
845 dlink = tf->linkage; 973 dlink = tf->linkage;
846 delegateCall = true; 974 delegateCall = true;
897 1025
898 // argument handling 1026 // argument handling
899 llvm::FunctionType::param_iterator argiter = llfnty->param_begin(); 1027 llvm::FunctionType::param_iterator argiter = llfnty->param_begin();
900 int j = 0; 1028 int j = 0;
901 1029
902 // hidden struct return parameter 1030 // hidden struct return arguments
903 if (retinptr) { 1031 if (retinptr) {
904 if (!p->lvals.empty()) { 1032 if (!p->lvals.empty()) {
905 assert(llvm::isa<llvm::StructType>(p->toplval()->getType()->getContainedType(0))); 1033 assert(llvm::isa<llvm::StructType>(p->toplval()->getType()->getContainedType(0)));
906 llargs[j] = p->toplval(); 1034 llargs[j] = p->toplval();
907 TY Dty = tf->next->ty; 1035 if (LLVM_DtoIsPassedByRef(tf->next)) {
908 if (Dty == Tstruct || Dty == Tdelegate || Dty == Tarray) {
909 e->inplace = true; 1036 e->inplace = true;
910 } 1037 }
911 else 1038 else
912 assert(0); 1039 assert(0);
913 } 1040 }
920 } 1047 }
921 else { 1048 else {
922 e->type = elem::VAL; 1049 e->type = elem::VAL;
923 } 1050 }
924 1051
925 // this parameter 1052 // this arguments
926 if (fn->arg) { 1053 if (fn->arg) {
927 Logger::println("This Call"); 1054 Logger::println("This Call");
928 if (fn->arg->getType() != argiter->get()) { 1055 if (fn->arg->getType() != argiter->get()) {
929 //Logger::cout() << *fn->thisparam << '|' << *argiter->get() << '\n'; 1056 //Logger::cout() << *fn->thisparam << '|' << *argiter->get() << '\n';
930 llargs[j] = new llvm::BitCastInst(fn->arg, argiter->get(), "tmp", p->scopebb()); 1057 llargs[j] = new llvm::BitCastInst(fn->arg, argiter->get(), "tmp", p->scopebb());
933 llargs[j] = fn->arg; 1060 llargs[j] = fn->arg;
934 } 1061 }
935 ++j; 1062 ++j;
936 ++argiter; 1063 ++argiter;
937 } 1064 }
938 // delegate context parameter 1065 // delegate context arguments
939 else if (delegateCall) { 1066 else if (delegateCall) {
940 Logger::println("Delegate Call"); 1067 Logger::println("Delegate Call");
941 llvm::Value* contextptr = LLVM_DtoGEP(fn->mem,zero,zero,"tmp",p->scopebb()); 1068 llvm::Value* contextptr = LLVM_DtoGEP(fn->mem,zero,zero,"tmp",p->scopebb());
942 llargs[j] = new llvm::LoadInst(contextptr,"tmp",p->scopebb()); 1069 llargs[j] = new llvm::LoadInst(contextptr,"tmp",p->scopebb());
943 ++j; 1070 ++j;
944 ++argiter; 1071 ++argiter;
945 } 1072 }
946 1073
947 // regular parameters 1074 // regular arguments
948 for (int i=0; i<arguments->dim; i++,j++) 1075 for (int i=0; i<arguments->dim; i++,j++)
949 { 1076 {
950 Expression* argexp = (Expression*)arguments->data[i];
951 elem* arg = argexp->toElem(p);
952 if (arg->inplace) {
953 assert(arg->mem);
954 llargs[j] = arg->mem;
955 continue;
956 }
957
958 Argument* fnarg = Argument::getNth(tf->parameters, i); 1077 Argument* fnarg = Argument::getNth(tf->parameters, i);
959 1078 llargs[j] = LLVM_DtoArgument(llfnty->getParamType(j), fnarg, (Expression*)arguments->data[i]);
960 TY argty = argexp->type->ty;
961 if (argty == Tstruct || argty == Tdelegate || argty == Tarray) {
962 if (!fnarg || !fnarg->llvmCopy) {
963 llargs[j] = arg->getValue();
964 assert(llargs[j] != 0);
965 }
966 else {
967 llvm::Value* allocaInst = 0;
968 llvm::BasicBlock* entryblock = &p->topfunc()->front();
969 const llvm::PointerType* pty = llvm::cast<llvm::PointerType>(arg->mem->getType());
970 if (argty == Tstruct) {
971 allocaInst = new llvm::AllocaInst(pty->getElementType(), "tmpparam", p->topallocapoint());
972 TypeStruct* ts = (TypeStruct*)argexp->type;
973 LLVM_DtoStructCopy(ts,allocaInst,arg->mem);
974 }
975 else if (argty == Tdelegate) {
976 allocaInst = new llvm::AllocaInst(pty->getElementType(), "tmpparam", p->topallocapoint());
977 LLVM_DtoDelegateCopy(allocaInst,arg->mem);
978 }
979 else if (argty == Tarray) {
980 if (arg->type == elem::SLICE) {
981 allocaInst = new llvm::AllocaInst(LLVM_DtoType(argexp->type), "tmpparam", p->topallocapoint());
982 LLVM_DtoSetArray(allocaInst, arg->arg, arg->mem);
983 }
984 else {
985 allocaInst = new llvm::AllocaInst(pty->getElementType(), "tmpparam", p->topallocapoint());
986 LLVM_DtoArrayAssign(allocaInst,arg->mem);
987 }
988 }
989 else
990 assert(0);
991
992 llargs[j] = allocaInst;
993 assert(llargs[j] != 0);
994 }
995 }
996 else if (!fnarg || fnarg->llvmCopy) {
997 Logger::println("regular arg");
998 assert(arg->type != elem::SLICE);
999 llargs[j] = arg->arg ? arg->arg : arg->getValue();
1000 assert(llargs[j] != 0);
1001 }
1002 else {
1003 Logger::println("as ptr arg");
1004 llargs[j] = arg->mem ? arg->mem : arg->val;
1005 if (llargs[j]->getType() != llfnty->getParamType(j))
1006 {
1007 assert(llargs[j]->getType() == llfnty->getParamType(j)->getContainedType(0));
1008 LLVM_DtoGiveArgumentStorage(arg);
1009 new llvm::StoreInst(llargs[j], arg->mem, p->scopebb());
1010 llargs[j] = arg->mem;
1011 }
1012 assert(llargs[j] != 0);
1013 }
1014
1015 delete arg;
1016 } 1079 }
1017 1080
1018 // void returns cannot not be named 1081 // void returns cannot not be named
1019 const char* varname = ""; 1082 const char* varname = "";
1020 if (llfnty->getReturnType() != llvm::Type::VoidTy) 1083 if (llfnty->getReturnType() != llvm::Type::VoidTy)
1051 { 1114 {
1052 Logger::print("CastExp::toElem: %s\n", toChars()); 1115 Logger::print("CastExp::toElem: %s\n", toChars());
1053 LOG_SCOPE; 1116 LOG_SCOPE;
1054 elem* e = new elem; 1117 elem* e = new elem;
1055 elem* u = e1->toElem(p); 1118 elem* u = e1->toElem(p);
1056 const llvm::Type* totype = LLVM_DtoType(to); 1119 const llvm::Type* tolltype = LLVM_DtoType(to);
1057 Type* from = e1->type; 1120 Type* fromtype = LLVM_DtoDType(e1->type);
1058 int lsz = from->size(); 1121 Type* totype = LLVM_DtoDType(to);
1059 int rsz = to->size(); 1122 int lsz = fromtype->size();
1123 int rsz = totype->size();
1060 1124
1061 // this makes sure the strange lvalue casts don't screw things up 1125 // this makes sure the strange lvalue casts don't screw things up
1062 e->mem = u->mem; 1126 e->mem = u->mem;
1063 1127
1064 if (from->isintegral()) { 1128 if (fromtype->isintegral()) {
1065 if (to->isintegral()) { 1129 if (totype->isintegral()) {
1066 if (lsz < rsz) { 1130 if (lsz < rsz) {
1067 Logger::cout() << *totype << '\n'; 1131 Logger::cout() << *tolltype << '\n';
1068 if (from->isunsigned() || from->ty == Tbool) { 1132 if (fromtype->isunsigned() || fromtype->ty == Tbool) {
1069 e->val = new llvm::ZExtInst(u->getValue(), totype, "tmp", p->scopebb()); 1133 e->val = new llvm::ZExtInst(u->getValue(), tolltype, "tmp", p->scopebb());
1070 } else { 1134 } else {
1071 e->val = new llvm::SExtInst(u->getValue(), totype, "tmp", p->scopebb()); 1135 e->val = new llvm::SExtInst(u->getValue(), tolltype, "tmp", p->scopebb());
1072 } 1136 }
1073 } 1137 }
1074 else if (lsz > rsz) { 1138 else if (lsz > rsz) {
1075 e->val = new llvm::TruncInst(u->getValue(), totype, "tmp", p->scopebb()); 1139 e->val = new llvm::TruncInst(u->getValue(), tolltype, "tmp", p->scopebb());
1076 } 1140 }
1077 else { 1141 else {
1078 e->val = new llvm::BitCastInst(u->getValue(), totype, "tmp", p->scopebb()); 1142 e->val = new llvm::BitCastInst(u->getValue(), tolltype, "tmp", p->scopebb());
1079 } 1143 }
1080 } 1144 }
1081 else if (to->isfloating()) { 1145 else if (totype->isfloating()) {
1082 if (from->isunsigned()) { 1146 if (fromtype->isunsigned()) {
1083 e->val = new llvm::UIToFPInst(u->getValue(), totype, "tmp", p->scopebb()); 1147 e->val = new llvm::UIToFPInst(u->getValue(), tolltype, "tmp", p->scopebb());
1084 } 1148 }
1085 else { 1149 else {
1086 e->val = new llvm::SIToFPInst(u->getValue(), totype, "tmp", p->scopebb()); 1150 e->val = new llvm::SIToFPInst(u->getValue(), tolltype, "tmp", p->scopebb());
1087 } 1151 }
1088 } 1152 }
1089 else { 1153 else {
1090 assert(0); 1154 assert(0);
1091 } 1155 }
1092 //e->storeVal = u->storeVal ? u->storeVal : u->val; 1156 //e->storeVal = u->storeVal ? u->storeVal : u->val;
1093 e->type = elem::VAL; 1157 e->type = elem::VAL;
1094 } 1158 }
1095 else if (from->isfloating()) { 1159 else if (fromtype->isfloating()) {
1096 if (to->isfloating()) { 1160 if (totype->isfloating()) {
1097 if ((from->ty == Tfloat80 || from->ty == Tfloat64) && (to->ty == Tfloat80 || to->ty == Tfloat64)) { 1161 if ((fromtype->ty == Tfloat80 || fromtype->ty == Tfloat64) && (totype->ty == Tfloat80 || totype->ty == Tfloat64)) {
1098 e->val = u->getValue(); 1162 e->val = u->getValue();
1099 } 1163 }
1100 else if (lsz < rsz) { 1164 else if (lsz < rsz) {
1101 e->val = new llvm::FPExtInst(u->getValue(), totype, "tmp", p->scopebb()); 1165 e->val = new llvm::FPExtInst(u->getValue(), tolltype, "tmp", p->scopebb());
1102 } 1166 }
1103 else if (lsz > rsz) { 1167 else if (lsz > rsz) {
1104 e->val = new llvm::FPTruncInst(u->getValue(), totype, "tmp", p->scopebb()); 1168 e->val = new llvm::FPTruncInst(u->getValue(), tolltype, "tmp", p->scopebb());
1105 } 1169 }
1106 else { 1170 else {
1107 assert(0); 1171 assert(0);
1108 } 1172 }
1109 } 1173 }
1110 else if (to->isintegral()) { 1174 else if (totype->isintegral()) {
1111 if (to->isunsigned()) { 1175 if (totype->isunsigned()) {
1112 e->val = new llvm::FPToUIInst(u->getValue(), totype, "tmp", p->scopebb()); 1176 e->val = new llvm::FPToUIInst(u->getValue(), tolltype, "tmp", p->scopebb());
1113 } 1177 }
1114 else { 1178 else {
1115 e->val = new llvm::FPToSIInst(u->getValue(), totype, "tmp", p->scopebb()); 1179 e->val = new llvm::FPToSIInst(u->getValue(), tolltype, "tmp", p->scopebb());
1116 } 1180 }
1117 } 1181 }
1118 else { 1182 else {
1119 assert(0); 1183 assert(0);
1120 } 1184 }
1121 e->type = elem::VAL; 1185 e->type = elem::VAL;
1122 } 1186 }
1123 else if (from->ty == Tclass) { 1187 else if (fromtype->ty == Tclass) {
1124 //assert(to->ty == Tclass); 1188 //assert(to->ty == Tclass);
1125 e->val = new llvm::BitCastInst(u->getValue(), totype, "tmp", p->scopebb()); 1189 e->val = new llvm::BitCastInst(u->getValue(), tolltype, "tmp", p->scopebb());
1126 e->type = elem::VAL; 1190 e->type = elem::VAL;
1127 } 1191 }
1128 else if (from->ty == Tarray || from->ty == Tsarray) { 1192 else if (fromtype->ty == Tarray || fromtype->ty == Tsarray) {
1129 Logger::cout() << "from array or sarray" << '\n'; 1193 Logger::cout() << "from array or sarray" << '\n';
1130 if (to->ty == Tpointer) { 1194 if (totype->ty == Tpointer) {
1131 Logger::cout() << "to pointer" << '\n'; 1195 Logger::cout() << "to pointer" << '\n';
1132 assert(from->next == to->next); 1196 assert(fromtype->next == totype->next);
1133 llvm::Value* zero = llvm::ConstantInt::get(llvm::Type::Int32Ty, 0, false); 1197 llvm::Value* zero = llvm::ConstantInt::get(llvm::Type::Int32Ty, 0, false);
1134 llvm::Value* one = llvm::ConstantInt::get(llvm::Type::Int32Ty, 1, false); 1198 llvm::Value* one = llvm::ConstantInt::get(llvm::Type::Int32Ty, 1, false);
1135 llvm::Value* ptr = LLVM_DtoGEP(u->getValue(),zero,one,"tmp",p->scopebb()); 1199 llvm::Value* ptr = LLVM_DtoGEP(u->getValue(),zero,one,"tmp",p->scopebb());
1136 e->val = new llvm::LoadInst(ptr, "tmp", p->scopebb()); 1200 e->val = new llvm::LoadInst(ptr, "tmp", p->scopebb());
1137 e->type = elem::VAL; 1201 e->type = elem::VAL;
1138 } 1202 }
1139 else if (to->ty == Tarray) { 1203 else if (totype->ty == Tarray) {
1140 Logger::cout() << "to array" << '\n'; 1204 Logger::cout() << "to array" << '\n';
1141 assert(from->next->size() == to->next->size()); 1205 assert(fromtype->next->size() == totype->next->size());
1142 const llvm::Type* ptrty = LLVM_DtoType(to->next); 1206 const llvm::Type* ptrty = LLVM_DtoType(totype->next);
1143 if (ptrty == llvm::Type::VoidTy) 1207 if (ptrty == llvm::Type::VoidTy)
1144 ptrty = llvm::Type::Int8Ty; 1208 ptrty = llvm::Type::Int8Ty;
1145 ptrty = llvm::PointerType::get(ptrty); 1209 ptrty = llvm::PointerType::get(ptrty);
1146 1210
1147 if (u->type == elem::SLICE) { 1211 if (u->type == elem::SLICE) {
1148 e->mem = new llvm::BitCastInst(u->mem, ptrty, "tmp", p->scopebb()); 1212 e->mem = new llvm::BitCastInst(u->mem, ptrty, "tmp", p->scopebb());
1149 e->arg = u->arg; 1213 e->arg = u->arg;
1150 } 1214 }
1151 else { 1215 else {
1152 llvm::Value* uval = u->getValue(); 1216 llvm::Value* uval = u->getValue();
1153 if (from->ty == Tsarray) { 1217 if (fromtype->ty == Tsarray) {
1154 Logger::cout() << "uvalTy = " << *uval->getType() << '\n'; 1218 Logger::cout() << "uvalTy = " << *uval->getType() << '\n';
1155 assert(llvm::isa<llvm::PointerType>(uval->getType())); 1219 assert(llvm::isa<llvm::PointerType>(uval->getType()));
1156 const llvm::ArrayType* arrty = llvm::cast<llvm::ArrayType>(uval->getType()->getContainedType(0)); 1220 const llvm::ArrayType* arrty = llvm::cast<llvm::ArrayType>(uval->getType()->getContainedType(0));
1157 e->arg = llvm::ConstantInt::get(LLVM_DtoSize_t(), arrty->getNumElements(), false); 1221 e->arg = llvm::ConstantInt::get(LLVM_DtoSize_t(), arrty->getNumElements(), false);
1158 e->mem = new llvm::BitCastInst(uval, ptrty, "tmp", p->scopebb()); 1222 e->mem = new llvm::BitCastInst(uval, ptrty, "tmp", p->scopebb());
1169 e->mem = new llvm::BitCastInst(e->mem, ptrty, "tmp", p->scopebb()); 1233 e->mem = new llvm::BitCastInst(e->mem, ptrty, "tmp", p->scopebb());
1170 } 1234 }
1171 } 1235 }
1172 e->type = elem::SLICE; 1236 e->type = elem::SLICE;
1173 } 1237 }
1174 else if (to->ty == Tsarray) { 1238 else if (totype->ty == Tsarray) {
1175 Logger::cout() << "to sarray" << '\n'; 1239 Logger::cout() << "to sarray" << '\n';
1176 assert(0); 1240 assert(0);
1177 } 1241 }
1178 else { 1242 else {
1179 assert(0); 1243 assert(0);
1180 } 1244 }
1181 } 1245 }
1182 else if (from->ty == Tpointer) { 1246 else if (fromtype->ty == Tpointer) {
1183 if (to->ty == Tpointer || to->ty == Tclass) { 1247 if (totype->ty == Tpointer || totype->ty == Tclass) {
1184 llvm::Value* src = u->getValue(); 1248 llvm::Value* src = u->getValue();
1185 //Logger::cout() << *src << '|' << *totype << '\n'; 1249 //Logger::cout() << *src << '|' << *totype << '\n';
1186 e->val = new llvm::BitCastInst(src, totype, "tmp", p->scopebb()); 1250 e->val = new llvm::BitCastInst(src, tolltype, "tmp", p->scopebb());
1187 } 1251 }
1188 else if (to->isintegral()) { 1252 else if (totype->isintegral()) {
1189 e->val = new llvm::PtrToIntInst(u->getValue(), totype, "tmp", p->scopebb()); 1253 e->val = new llvm::PtrToIntInst(u->getValue(), tolltype, "tmp", p->scopebb());
1190 } 1254 }
1191 else 1255 else
1192 assert(0); 1256 assert(0);
1193 e->type = elem::VAL; 1257 e->type = elem::VAL;
1194 } 1258 }
1208 elem* e = 0; 1272 elem* e = 0;
1209 if (VarDeclaration* vd = var->isVarDeclaration()) 1273 if (VarDeclaration* vd = var->isVarDeclaration())
1210 { 1274 {
1211 Logger::println("VarDeclaration"); 1275 Logger::println("VarDeclaration");
1212 assert(vd->llvmValue); 1276 assert(vd->llvmValue);
1213 if (vd->type->ty == Tstruct && !(type->ty == Tpointer && type->next == vd->type)) { 1277 Type* t = LLVM_DtoDType(type);
1214 TypeStruct* vdt = (TypeStruct*)vd->type; 1278 Type* vdtype = LLVM_DtoDType(vd->type);
1279 if (vdtype->ty == Tstruct && !(t->ty == Tpointer && t->next == vdtype)) {
1280 TypeStruct* vdt = (TypeStruct*)vdtype;
1215 e = new elem; 1281 e = new elem;
1216 std::vector<unsigned> dst(1,0); 1282 std::vector<unsigned> dst(1,0);
1217 vdt->sym->offsetToIndex(type->next, offset, dst); 1283 vdt->sym->offsetToIndex(t->next, offset, dst);
1218 llvm::Value* ptr = vd->llvmValue; 1284 llvm::Value* ptr = vd->llvmValue;
1219 assert(ptr); 1285 assert(ptr);
1220 e->mem = LLVM_DtoGEP(ptr,dst,"tmp",p->scopebb()); 1286 e->mem = LLVM_DtoGEP(ptr,dst,"tmp",p->scopebb());
1221 e->type = elem::VAL; 1287 e->type = elem::VAL;
1222 e->field = true; 1288 e->field = true;
1223 } 1289 }
1224 else if (vd->type->ty == Tsarray) { 1290 else if (vdtype->ty == Tsarray) {
1225 /*e = new elem; 1291 /*e = new elem;
1226 llvm::Value* idx0 = llvm::ConstantInt::get(llvm::Type::Int32Ty, 0, false); 1292 llvm::Value* idx0 = llvm::ConstantInt::get(llvm::Type::Int32Ty, 0, false);
1227 e->val = new llvm::GetElementPtrInst(vd->llvmValue,idx0,idx0,"tmp",p->scopebb());*/ 1293 e->val = new llvm::GetElementPtrInst(vd->llvmValue,idx0,idx0,"tmp",p->scopebb());*/
1228 e = new elem; 1294 e = new elem;
1229 llvm::Value* idx0 = llvm::ConstantInt::get(llvm::Type::Int32Ty, 0, false); 1295 llvm::Value* idx0 = llvm::ConstantInt::get(llvm::Type::Int32Ty, 0, false);
1292 LOG_SCOPE; 1358 LOG_SCOPE;
1293 elem* e = new elem; 1359 elem* e = new elem;
1294 1360
1295 elem* l = e1->toElem(p); 1361 elem* l = e1->toElem(p);
1296 1362
1297 Logger::print("e1->type=%s\n", e1->type->toChars()); 1363 Type* t = LLVM_DtoDType(type);
1364 Type* e1type = LLVM_DtoDType(e1->type);
1365
1366 Logger::print("e1->type=%s\n", e1type->toChars());
1298 1367
1299 if (VarDeclaration* vd = var->isVarDeclaration()) { 1368 if (VarDeclaration* vd = var->isVarDeclaration()) {
1300 std::vector<unsigned> vdoffsets(1,0); 1369 std::vector<unsigned> vdoffsets(1,0);
1301 llvm::Value* src = 0; 1370 llvm::Value* src = 0;
1302 if (e1->type->ty == Tpointer) { 1371 if (e1type->ty == Tpointer) {
1303 assert(e1->type->next->ty == Tstruct); 1372 assert(e1type->next->ty == Tstruct);
1304 TypeStruct* ts = (TypeStruct*)e1->type->next; 1373 TypeStruct* ts = (TypeStruct*)e1type->next;
1305 ts->sym->offsetToIndex(vd->type, vd->offset, vdoffsets); 1374 ts->sym->offsetToIndex(vd->type, vd->offset, vdoffsets);
1306 Logger::println("Struct member offset:%d", vd->offset); 1375 Logger::println("Struct member offset:%d", vd->offset);
1307 src = l->val ? l->val : l->mem; 1376 src = l->val ? l->val : l->mem;
1308 } 1377 }
1309 else if (e1->type->ty == Tclass) { 1378 else if (e1->type->ty == Tclass) {
1310 TypeClass* tc = (TypeClass*)e1->type; 1379 TypeClass* tc = (TypeClass*)e1type;
1311 Logger::println("Class member offset: %d", vd->offset); 1380 Logger::println("Class member offset: %d", vd->offset);
1312 tc->sym->offsetToIndex(vd->type, vd->offset, vdoffsets); 1381 tc->sym->offsetToIndex(vd->type, vd->offset, vdoffsets);
1313 src = l->getValue(); 1382 src = l->getValue();
1314 } 1383 }
1315 assert(vdoffsets.size() != 1); 1384 assert(vdoffsets.size() != 1);
1316 assert(src != 0); 1385 assert(src != 0);
1386 Logger::cout() << "src: " << *src << '\n';
1317 llvm::Value* arrptr = LLVM_DtoGEP(src,vdoffsets,"tmp",p->scopebb()); 1387 llvm::Value* arrptr = LLVM_DtoGEP(src,vdoffsets,"tmp",p->scopebb());
1318 e->mem = arrptr; 1388 e->mem = arrptr;
1319 Logger::cout() << "mem: " << *e->mem << '\n'; 1389 Logger::cout() << "mem: " << *e->mem << '\n';
1320 e->type = elem::VAR; 1390 e->type = elem::VAR;
1321 } 1391 }
1330 e->arg = l->getValue(); 1400 e->arg = l->getValue();
1331 1401
1332 // virtual call 1402 // virtual call
1333 if (fdecl->isVirtual()) { 1403 if (fdecl->isVirtual()) {
1334 assert(fdecl->vtblIndex > 0); 1404 assert(fdecl->vtblIndex > 0);
1335 assert(e1->type->ty == Tclass); 1405 assert(e1type->ty == Tclass);
1336 1406
1337 llvm::Value* zero = llvm::ConstantInt::get(llvm::Type::Int32Ty, 0, false); 1407 llvm::Value* zero = llvm::ConstantInt::get(llvm::Type::Int32Ty, 0, false);
1338 llvm::Value* vtblidx = llvm::ConstantInt::get(llvm::Type::Int32Ty, (size_t)fdecl->vtblIndex, false); 1408 llvm::Value* vtblidx = llvm::ConstantInt::get(llvm::Type::Int32Ty, (size_t)fdecl->vtblIndex, false);
1339 funcval = LLVM_DtoGEP(e->arg, zero, zero, "tmp", p->scopebb()); 1409 funcval = LLVM_DtoGEP(e->arg, zero, zero, "tmp", p->scopebb());
1340 funcval = new llvm::LoadInst(funcval,"tmp",p->scopebb()); 1410 funcval = new llvm::LoadInst(funcval,"tmp",p->scopebb());
1363 Logger::print("ThisExp::toElem: %s | %s\n", toChars(), type->toChars()); 1433 Logger::print("ThisExp::toElem: %s | %s\n", toChars(), type->toChars());
1364 LOG_SCOPE; 1434 LOG_SCOPE;
1365 elem* e = new elem; 1435 elem* e = new elem;
1366 1436
1367 if (VarDeclaration* vd = var->isVarDeclaration()) { 1437 if (VarDeclaration* vd = var->isVarDeclaration()) {
1368 /*assert(vd->llvmValue == 0); 1438 llvm::Value* v = p->func().decl->llvmThisVar;
1369
1370 llvm::Function* fn = p->topfunc();
1371 assert(fn);
1372
1373 TypeFunction* tf = p->topfunctype();
1374 assert(tf);
1375
1376 llvm::Value* v = 0;
1377 if (tf->llvmRetInPtr)
1378 v = ++fn->arg_begin();
1379 else
1380 v = fn->arg_begin();
1381 assert(v);*/
1382
1383 llvm::Value* v = p->funcdecls.back()->llvmThisVar;
1384 if (llvm::isa<llvm::AllocaInst>(v)) 1439 if (llvm::isa<llvm::AllocaInst>(v))
1385 v = new llvm::LoadInst(v, "tmp", p->scopebb()); 1440 v = new llvm::LoadInst(v, "tmp", p->scopebb());
1386 e->mem = v; 1441 e->mem = v;
1387 e->type = elem::VAL; 1442 e->type = elem::VAL;
1388 e->isthis = true; 1443 e->isthis = true;
1438 llvm::Value* offset = llvm::ConstantInt::get(llvm::Type::Int32Ty, i, false); 1493 llvm::Value* offset = llvm::ConstantInt::get(llvm::Type::Int32Ty, i, false);
1439 llvm::Value* arrptr = LLVM_DtoGEP(sptr,zero,offset,"tmp",p->scopebb()); 1494 llvm::Value* arrptr = LLVM_DtoGEP(sptr,zero,offset,"tmp",p->scopebb());
1440 1495
1441 Expression* vx = (Expression*)elements->data[i]; 1496 Expression* vx = (Expression*)elements->data[i];
1442 if (vx != 0) { 1497 if (vx != 0) {
1498 p->lvals.push_back(arrptr);
1443 elem* ve = vx->toElem(p); 1499 elem* ve = vx->toElem(p);
1444 llvm::Value* val = ve->getValue(); 1500 p->lvals.pop_back();
1445 Logger::cout() << *val << " | " << *arrptr << '\n'; 1501
1446 if (vx->type->ty == Tstruct) { 1502 if (!ve->inplace) {
1447 TypeStruct* ts = (TypeStruct*)vx->type; 1503 llvm::Value* val = ve->getValue();
1448 LLVM_DtoStructCopy(ts,arrptr,val); 1504 Logger::cout() << *val << " | " << *arrptr << '\n';
1449 } 1505
1450 else 1506 Type* vxtype = LLVM_DtoDType(vx->type);
1451 new llvm::StoreInst(val, arrptr, p->scopebb()); 1507 if (vxtype->ty == Tstruct) {
1508 TypeStruct* ts = (TypeStruct*)vxtype;
1509 LLVM_DtoStructCopy(ts,arrptr,val);
1510 }
1511 else
1512 new llvm::StoreInst(val, arrptr, p->scopebb());
1513 }
1452 delete ve; 1514 delete ve;
1453 } 1515 }
1454 else { 1516 else {
1455 assert(0); 1517 assert(0);
1456 } 1518 }
1461 return e; 1523 return e;
1462 } 1524 }
1463 1525
1464 ////////////////////////////////////////////////////////////////////////////////////////// 1526 //////////////////////////////////////////////////////////////////////////////////////////
1465 1527
1528 llvm::Constant* StructLiteralExp::toConstElem(IRState* p)
1529 {
1530 Logger::print("StructLiteralExp::toConstElem: %s | %s\n", toChars(), type->toChars());
1531 LOG_SCOPE;
1532
1533 unsigned n = elements->dim;
1534 std::vector<llvm::Constant*> vals(n, NULL);
1535
1536 for (unsigned i=0; i<n; ++i)
1537 {
1538 Expression* vx = (Expression*)elements->data[i];
1539 vals[i] = vx->toConstElem(p);
1540 }
1541
1542 assert(LLVM_DtoDType(type)->ty == Tstruct);
1543 const llvm::Type* t = LLVM_DtoType(type);
1544 const llvm::StructType* st = llvm::cast<llvm::StructType>(t);
1545 return llvm::ConstantStruct::get(st,vals);
1546 }
1547
1548 //////////////////////////////////////////////////////////////////////////////////////////
1549
1466 elem* IndexExp::toElem(IRState* p) 1550 elem* IndexExp::toElem(IRState* p)
1467 { 1551 {
1468 Logger::print("IndexExp::toElem: %s | %s\n", toChars(), type->toChars()); 1552 Logger::print("IndexExp::toElem: %s | %s\n", toChars(), type->toChars());
1469 LOG_SCOPE; 1553 LOG_SCOPE;
1470 1554
1471 elem* e = new elem; 1555 elem* e = new elem;
1472 1556
1473 elem* l = e1->toElem(p); 1557 elem* l = e1->toElem(p);
1558
1559 Type* e1type = LLVM_DtoDType(e1->type);
1474 1560
1475 p->arrays.push_back(l->mem); // if $ is used it must be an array so this is fine. 1561 p->arrays.push_back(l->mem); // if $ is used it must be an array so this is fine.
1476 elem* r = e2->toElem(p); 1562 elem* r = e2->toElem(p);
1477 p->arrays.pop_back(); 1563 p->arrays.pop_back();
1478 1564
1479 llvm::Value* zero = llvm::ConstantInt::get(llvm::Type::Int32Ty, 0, false); 1565 llvm::Value* zero = llvm::ConstantInt::get(llvm::Type::Int32Ty, 0, false);
1480 llvm::Value* one = llvm::ConstantInt::get(llvm::Type::Int32Ty, 1, false); 1566 llvm::Value* one = llvm::ConstantInt::get(llvm::Type::Int32Ty, 1, false);
1481 1567
1482 llvm::Value* arrptr = 0; 1568 llvm::Value* arrptr = 0;
1483 if (e1->type->ty == Tpointer) { 1569 if (e1type->ty == Tpointer) {
1484 arrptr = new llvm::GetElementPtrInst(l->getValue(),r->getValue(),"tmp",p->scopebb()); 1570 arrptr = new llvm::GetElementPtrInst(l->getValue(),r->getValue(),"tmp",p->scopebb());
1485 } 1571 }
1486 else if (e1->type->ty == Tsarray) { 1572 else if (e1type->ty == Tsarray) {
1487 arrptr = LLVM_DtoGEP(l->mem, zero, r->getValue(),"tmp",p->scopebb()); 1573 arrptr = LLVM_DtoGEP(l->getValue(), zero, r->getValue(),"tmp",p->scopebb());
1488 } 1574 }
1489 else if (e1->type->ty == Tarray) { 1575 else if (e1type->ty == Tarray) {
1490 arrptr = LLVM_DtoGEP(l->mem,zero,one,"tmp",p->scopebb()); 1576 arrptr = LLVM_DtoGEP(l->mem,zero,one,"tmp",p->scopebb());
1491 arrptr = new llvm::LoadInst(arrptr,"tmp",p->scopebb()); 1577 arrptr = new llvm::LoadInst(arrptr,"tmp",p->scopebb());
1492 arrptr = new llvm::GetElementPtrInst(arrptr,r->getValue(),"tmp",p->scopebb()); 1578 arrptr = new llvm::GetElementPtrInst(arrptr,r->getValue(),"tmp",p->scopebb());
1493 } 1579 }
1494 assert(arrptr); 1580 assert(arrptr);
1508 { 1594 {
1509 Logger::print("SliceExp::toElem: %s | %s\n", toChars(), type->toChars()); 1595 Logger::print("SliceExp::toElem: %s | %s\n", toChars(), type->toChars());
1510 LOG_SCOPE; 1596 LOG_SCOPE;
1511 1597
1512 elem* v = e1->toElem(p); 1598 elem* v = e1->toElem(p);
1599 Type* e1type = LLVM_DtoDType(e1->type);
1513 1600
1514 elem* e = new elem; 1601 elem* e = new elem;
1515 assert(v->mem); 1602 assert(v->mem);
1516 e->type = elem::SLICE; 1603 e->type = elem::SLICE;
1517 1604
1529 if (lo->type == elem::CONST) 1616 if (lo->type == elem::CONST)
1530 { 1617 {
1531 assert(lo->val); 1618 assert(lo->val);
1532 assert(llvm::isa<llvm::ConstantInt>(lo->val)); 1619 assert(llvm::isa<llvm::ConstantInt>(lo->val));
1533 1620
1534 if (e1->type->ty == Tpointer) { 1621 if (e1type->ty == Tpointer) {
1535 e->mem = v->getValue(); 1622 e->mem = v->getValue();
1536 } 1623 }
1537 else if (e1->type->ty == Tarray) { 1624 else if (e1type->ty == Tarray) {
1538 llvm::Value* tmp = LLVM_DtoGEP(v->mem,zero,one,"tmp",p->scopebb()); 1625 llvm::Value* tmp = LLVM_DtoGEP(v->mem,zero,one,"tmp",p->scopebb());
1539 e->mem = new llvm::LoadInst(tmp,"tmp",p->scopebb()); 1626 e->mem = new llvm::LoadInst(tmp,"tmp",p->scopebb());
1627 }
1628 else if (e1type->ty == Tsarray) {
1629 e->mem = LLVM_DtoGEP(v->mem,zero,zero,"tmp",p->scopebb());
1540 } 1630 }
1541 else 1631 else
1542 assert(e->mem); 1632 assert(e->mem);
1543 1633
1544 llvm::ConstantInt* c = llvm::cast<llvm::ConstantInt>(lo->val); 1634 llvm::ConstantInt* c = llvm::cast<llvm::ConstantInt>(lo->val);
1546 e->mem = new llvm::GetElementPtrInst(e->mem,lo->val,"tmp",p->scopebb()); 1636 e->mem = new llvm::GetElementPtrInst(e->mem,lo->val,"tmp",p->scopebb());
1547 } 1637 }
1548 } 1638 }
1549 else 1639 else
1550 { 1640 {
1551 llvm::Value* tmp = LLVM_DtoGEP(v->mem,zero,one,"tmp",p->scopebb()); 1641 if (e1type->ty == Tarray) {
1552 tmp = new llvm::LoadInst(tmp,"tmp",p->scopebb()); 1642 llvm::Value* tmp = LLVM_DtoGEP(v->mem,zero,one,"tmp",p->scopebb());
1553 e->mem = new llvm::GetElementPtrInst(tmp,lo->getValue(),"tmp",p->scopebb()); 1643 tmp = new llvm::LoadInst(tmp,"tmp",p->scopebb());
1644 e->mem = new llvm::GetElementPtrInst(tmp,lo->getValue(),"tmp",p->scopebb());
1645 }
1646 else if (e1type->ty == Tsarray) {
1647 e->mem = LLVM_DtoGEP(v->mem,zero,lo->getValue(),"tmp",p->scopebb());
1648 }
1649 else
1650 assert(0);
1554 } 1651 }
1555 1652
1556 elem* up = upr->toElem(p); 1653 elem* up = upr->toElem(p);
1557 p->arrays.pop_back(); 1654 p->arrays.pop_back();
1558 1655
1608 elem* e = new elem; 1705 elem* e = new elem;
1609 1706
1610 elem* l = e1->toElem(p); 1707 elem* l = e1->toElem(p);
1611 elem* r = e2->toElem(p); 1708 elem* r = e2->toElem(p);
1612 1709
1613 assert(e1->type == e2->type); 1710 Type* t = LLVM_DtoDType(e1->type);
1614 1711 Type* e2t = LLVM_DtoDType(e2->type);
1615 Type* t = e1->type; 1712 assert(t == e2t);
1616 1713
1617 if (t->isintegral()) 1714 if (t->isintegral())
1618 { 1715 {
1619 llvm::ICmpInst::Predicate cmpop; 1716 llvm::ICmpInst::Predicate cmpop;
1717 bool skip = false;
1620 switch(op) 1718 switch(op)
1621 { 1719 {
1622 case TOKlt: 1720 case TOKlt:
1721 case TOKul:
1623 cmpop = t->isunsigned() ? llvm::ICmpInst::ICMP_ULT : llvm::ICmpInst::ICMP_SLT; 1722 cmpop = t->isunsigned() ? llvm::ICmpInst::ICMP_ULT : llvm::ICmpInst::ICMP_SLT;
1624 break; 1723 break;
1625 case TOKle: 1724 case TOKle:
1725 case TOKule:
1626 cmpop = t->isunsigned() ? llvm::ICmpInst::ICMP_ULE : llvm::ICmpInst::ICMP_SLE; 1726 cmpop = t->isunsigned() ? llvm::ICmpInst::ICMP_ULE : llvm::ICmpInst::ICMP_SLE;
1627 break; 1727 break;
1628 case TOKgt: 1728 case TOKgt:
1729 case TOKug:
1629 cmpop = t->isunsigned() ? llvm::ICmpInst::ICMP_UGT : llvm::ICmpInst::ICMP_SGT; 1730 cmpop = t->isunsigned() ? llvm::ICmpInst::ICMP_UGT : llvm::ICmpInst::ICMP_SGT;
1630 break; 1731 break;
1631 case TOKge: 1732 case TOKge:
1733 case TOKuge:
1632 cmpop = t->isunsigned() ? llvm::ICmpInst::ICMP_UGE : llvm::ICmpInst::ICMP_SGE; 1734 cmpop = t->isunsigned() ? llvm::ICmpInst::ICMP_UGE : llvm::ICmpInst::ICMP_SGE;
1633 break; 1735 break;
1736 case TOKue:
1737 cmpop = llvm::ICmpInst::ICMP_EQ;
1738 break;
1739 case TOKlg:
1740 cmpop = llvm::ICmpInst::ICMP_NE;
1741 break;
1742 case TOKleg:
1743 skip = true;
1744 e->val = llvm::ConstantInt::getTrue();
1745 break;
1746 case TOKunord:
1747 skip = true;
1748 e->val = llvm::ConstantInt::getFalse();
1749 break;
1750
1634 default: 1751 default:
1635 assert(0); 1752 assert(0);
1636 } 1753 }
1637 e->val = new llvm::ICmpInst(cmpop, l->getValue(), r->getValue(), "tmp", p->scopebb()); 1754 if (!skip)
1755 {
1756 e->val = new llvm::ICmpInst(cmpop, l->getValue(), r->getValue(), "tmp", p->scopebb());
1757 }
1638 } 1758 }
1639 else if (t->isfloating()) 1759 else if (t->isfloating())
1640 { 1760 {
1641 llvm::FCmpInst::Predicate cmpop; 1761 llvm::FCmpInst::Predicate cmpop;
1642 switch(op) 1762 switch(op)
1694 elem* e = new elem; 1814 elem* e = new elem;
1695 1815
1696 elem* l = e1->toElem(p); 1816 elem* l = e1->toElem(p);
1697 elem* r = e2->toElem(p); 1817 elem* r = e2->toElem(p);
1698 1818
1699 assert(e1->type == e2->type); 1819 Type* t = LLVM_DtoDType(e1->type);
1700 1820 Type* e2t = LLVM_DtoDType(e2->type);
1701 Type* t = e1->type; 1821 assert(t == e2t);
1702 1822
1703 if (t->isintegral() || t->ty == Tpointer) 1823 if (t->isintegral() || t->ty == Tpointer)
1704 { 1824 {
1705 llvm::ICmpInst::Predicate cmpop; 1825 llvm::ICmpInst::Predicate cmpop;
1706 switch(op) 1826 switch(op)
1730 default: 1850 default:
1731 assert(0); 1851 assert(0);
1732 } 1852 }
1733 e->val = new llvm::FCmpInst(cmpop, l->getValue(), r->getValue(), "tmp", p->scopebb()); 1853 e->val = new llvm::FCmpInst(cmpop, l->getValue(), r->getValue(), "tmp", p->scopebb());
1734 } 1854 }
1855 else if (t->ty == Tsarray)
1856 {
1857 e->val = LLVM_DtoStaticArrayCompare(op,l->mem,r->mem);
1858 }
1735 else if (t->ty == Tarray) 1859 else if (t->ty == Tarray)
1736 { 1860 {
1737 // array comparison invokes the typeinfo runtime 1861 assert(0 && "array comparison invokes the typeinfo runtime");
1738 assert(0);
1739 } 1862 }
1740 else 1863 else
1741 { 1864 {
1742 assert(0 && "Unsupported EqualExp type"); 1865 assert(0 && "Unsupported EqualExp type");
1743 } 1866 }
1766 e->type = elem::VAL; 1889 e->type = elem::VAL;
1767 1890
1768 llvm::Value* val = e->val; 1891 llvm::Value* val = e->val;
1769 llvm::Value* post = 0; 1892 llvm::Value* post = 0;
1770 1893
1771 if (e1->type->isintegral()) 1894 Type* e1type = LLVM_DtoDType(e1->type);
1772 { 1895 Type* e2type = LLVM_DtoDType(e2->type);
1773 assert(e2->type->isintegral()); 1896
1774 llvm::Value* one = llvm::ConstantInt::get(val->getType(), 1, !e2->type->isunsigned()); 1897 if (e1type->isintegral())
1898 {
1899 assert(e2type->isintegral());
1900 llvm::Value* one = llvm::ConstantInt::get(val->getType(), 1, !e2type->isunsigned());
1775 if (op == TOKplusplus) { 1901 if (op == TOKplusplus) {
1776 post = llvm::BinaryOperator::createAdd(val,one,"tmp",p->scopebb()); 1902 post = llvm::BinaryOperator::createAdd(val,one,"tmp",p->scopebb());
1777 } 1903 }
1778 else if (op == TOKminusminus) { 1904 else if (op == TOKminusminus) {
1779 post = llvm::BinaryOperator::createSub(val,one,"tmp",p->scopebb()); 1905 post = llvm::BinaryOperator::createSub(val,one,"tmp",p->scopebb());
1780 } 1906 }
1781 } 1907 }
1782 else if (e1->type->ty == Tpointer) 1908 else if (e1type->ty == Tpointer)
1783 { 1909 {
1784 assert(e2->type->isintegral()); 1910 assert(e2type->isintegral());
1785 llvm::Constant* minusone = llvm::ConstantInt::get(LLVM_DtoSize_t(),(uint64_t)-1,true); 1911 llvm::Constant* minusone = llvm::ConstantInt::get(LLVM_DtoSize_t(),(uint64_t)-1,true);
1786 llvm::Constant* plusone = llvm::ConstantInt::get(LLVM_DtoSize_t(),(uint64_t)1,false); 1912 llvm::Constant* plusone = llvm::ConstantInt::get(LLVM_DtoSize_t(),(uint64_t)1,false);
1787 llvm::Constant* whichone = (op == TOKplusplus) ? plusone : minusone; 1913 llvm::Constant* whichone = (op == TOKplusplus) ? plusone : minusone;
1788 post = new llvm::GetElementPtrInst(val, whichone, "tmp", p->scopebb()); 1914 post = new llvm::GetElementPtrInst(val, whichone, "tmp", p->scopebb());
1789 } 1915 }
1790 else if (e1->type->isfloating()) 1916 else if (e1type->isfloating())
1791 { 1917 {
1792 assert(e2->type->isfloating()); 1918 assert(e2type->isfloating());
1793 llvm::Value* one = llvm::ConstantFP::get(val->getType(), 1.0f); 1919 llvm::Value* one = llvm::ConstantFP::get(val->getType(), 1.0f);
1794 if (op == TOKplusplus) { 1920 if (op == TOKplusplus) {
1795 post = llvm::BinaryOperator::createAdd(val,one,"tmp",p->scopebb()); 1921 post = llvm::BinaryOperator::createAdd(val,one,"tmp",p->scopebb());
1796 } 1922 }
1797 else if (op == TOKminusminus) { 1923 else if (op == TOKminusminus) {
1818 LOG_SCOPE; 1944 LOG_SCOPE;
1819 1945
1820 assert(!thisexp); 1946 assert(!thisexp);
1821 assert(!newargs); 1947 assert(!newargs);
1822 assert(newtype); 1948 assert(newtype);
1823 //assert(!arguments);
1824 //assert(!member);
1825 assert(!allocator); 1949 assert(!allocator);
1826 1950
1827 elem* e = new elem; 1951 elem* e = new elem;
1828 1952
1829 const llvm::Type* t = LLVM_DtoType(newtype); 1953 Type* ntype = LLVM_DtoDType(newtype);
1954
1955 const llvm::Type* t = LLVM_DtoType(ntype);
1830 1956
1831 if (onstack) { 1957 if (onstack) {
1832 assert(newtype->ty == Tclass); 1958 assert(ntype->ty == Tclass);
1833 e->mem = new llvm::AllocaInst(t->getContainedType(0),"tmp",p->topallocapoint()); 1959 e->mem = new llvm::AllocaInst(t->getContainedType(0),"tmp",p->topallocapoint());
1834 } 1960 }
1835 else { 1961 else {
1836 if (newtype->ty == Tclass) { 1962 if (ntype->ty == Tclass) {
1837 e->mem = new llvm::MallocInst(t->getContainedType(0),"tmp",p->scopebb()); 1963 e->mem = new llvm::MallocInst(t->getContainedType(0),"tmp",p->scopebb());
1838 } 1964 }
1839 else if (newtype->ty == Tarray) { 1965 else if (ntype->ty == Tarray) {
1840 assert(arguments); 1966 assert(arguments);
1841 if (arguments->dim == 1) { 1967 if (arguments->dim == 1) {
1842 elem* sz = ((Expression*)arguments->data[0])->toElem(p); 1968 elem* sz = ((Expression*)arguments->data[0])->toElem(p);
1843 llvm::Value* dimval = sz->getValue(); 1969 llvm::Value* dimval = sz->getValue();
1844 LLVM_DtoNewDynArray(p->toplval(), dimval, newtype->next); 1970 LLVM_DtoNewDynArray(p->toplval(), dimval, ntype->next);
1845 delete sz; 1971 delete sz;
1846 } 1972 }
1847 else { 1973 else {
1848 assert(0); 1974 assert(0);
1849 } 1975 }
1851 else { 1977 else {
1852 e->mem = new llvm::MallocInst(t,"tmp",p->scopebb()); 1978 e->mem = new llvm::MallocInst(t,"tmp",p->scopebb());
1853 } 1979 }
1854 } 1980 }
1855 1981
1856 if (newtype->ty == Tclass) { 1982 if (ntype->ty == Tclass) {
1857 // first apply the static initializer 1983 // first apply the static initializer
1858 assert(e->mem); 1984 assert(e->mem);
1859 LLVM_DtoInitClass((TypeClass*)newtype, e->mem); 1985 LLVM_DtoInitClass((TypeClass*)ntype, e->mem);
1860 1986
1861 // then call constructor 1987 // then call constructor
1862 if (arguments) { 1988 if (arguments) {
1989 assert(member);
1990 assert(member->llvmValue);
1991 llvm::Function* fn = llvm::cast<llvm::Function>(member->llvmValue);
1992 TypeFunction* tf = (TypeFunction*)LLVM_DtoDType(member->type);
1993
1863 std::vector<llvm::Value*> ctorargs; 1994 std::vector<llvm::Value*> ctorargs;
1864 ctorargs.push_back(e->mem); 1995 ctorargs.push_back(e->mem);
1865 for (size_t i=0; i<arguments->dim; ++i) 1996 for (size_t i=0; i<arguments->dim; ++i)
1866 { 1997 {
1867 Expression* ex = (Expression*)arguments->data[i]; 1998 Expression* ex = (Expression*)arguments->data[i];
1868 Logger::println("arg=%s", ex->toChars()); 1999 Argument* fnarg = Argument::getNth(tf->parameters, i);
1869 elem* exe = ex->toElem(p); 2000 llvm::Value* a = LLVM_DtoArgument(fn->getFunctionType()->getParamType(i+1), fnarg, ex);
1870 llvm::Value* v = exe->getValue(); 2001 ctorargs.push_back(a);
1871 assert(v); 2002 }
1872 ctorargs.push_back(v); 2003 e->mem = new llvm::CallInst(fn, ctorargs.begin(), ctorargs.end(), "tmp", p->scopebb());
1873 delete exe; 2004 }
1874 } 2005 }
1875 assert(member); 2006 else if (ntype->ty == Tstruct) {
1876 assert(member->llvmValue); 2007 TypeStruct* ts = (TypeStruct*)ntype;
1877 e->mem = new llvm::CallInst(member->llvmValue, ctorargs.begin(), ctorargs.end(), "tmp", p->scopebb());
1878 }
1879 }
1880 else if (newtype->ty == Tstruct) {
1881 TypeStruct* ts = (TypeStruct*)newtype;
1882 if (ts->isZeroInit()) { 2008 if (ts->isZeroInit()) {
1883 LLVM_DtoStructZeroInit(ts,e->mem); 2009 LLVM_DtoStructZeroInit(ts,e->mem);
1884 } 2010 }
1885 else { 2011 else {
1886 LLVM_DtoStructCopy(ts,e->mem,ts->llvmInit); 2012 LLVM_DtoStructCopy(ts,e->mem,ts->llvmInit);
1907 llvm::Value* ldval = 0; 2033 llvm::Value* ldval = 0;
1908 2034
1909 const llvm::Type* t = val->getType(); 2035 const llvm::Type* t = val->getType();
1910 llvm::Constant* z = llvm::Constant::getNullValue(t); 2036 llvm::Constant* z = llvm::Constant::getNullValue(t);
1911 2037
1912 if (e1->type->ty == Tpointer) { 2038 Type* e1type = LLVM_DtoDType(e1->type);
2039
2040 if (e1type->ty == Tpointer) {
1913 ldval = v->getValue(); 2041 ldval = v->getValue();
1914 new llvm::FreeInst(ldval, p->scopebb()); 2042 new llvm::FreeInst(ldval, p->scopebb());
1915 2043
1916 Logger::cout() << *z << '\n'; 2044 Logger::cout() << *z << '\n';
1917 Logger::cout() << *val << '\n'; 2045 Logger::cout() << *val << '\n';
1918 new llvm::StoreInst(z, v->mem, p->scopebb()); 2046 new llvm::StoreInst(z, v->mem, p->scopebb());
1919 } 2047 }
1920 else if (e1->type->ty == Tclass) { 2048 else if (e1type->ty == Tclass) {
1921 TypeClass* tc = (TypeClass*)e1->type; 2049 TypeClass* tc = (TypeClass*)e1type;
1922 LLVM_DtoCallClassDtors(tc, val); 2050 LLVM_DtoCallClassDtors(tc, val);
1923 2051
1924 if (v->vardecl && !v->vardecl->onstack) { 2052 if (v->vardecl && !v->vardecl->onstack) {
1925 new llvm::FreeInst(val, p->scopebb()); 2053 new llvm::FreeInst(val, p->scopebb());
1926 } 2054 }
1927 new llvm::StoreInst(z, v->mem, p->scopebb()); 2055 new llvm::StoreInst(z, v->mem, p->scopebb());
1928 } 2056 }
1929 else if (e1->type->ty == Tarray) { 2057 else if (e1type->ty == Tarray) {
1930 // must be on the heap (correct?) 2058 // must be on the heap (correct?)
1931 ldval = v->getValue(); 2059 ldval = v->getValue();
1932 2060
1933 llvm::Value* zero = llvm::ConstantInt::get(llvm::Type::Int32Ty, 0, false); 2061 llvm::Value* zero = llvm::ConstantInt::get(llvm::Type::Int32Ty, 0, false);
1934 llvm::Value* one = llvm::ConstantInt::get(llvm::Type::Int32Ty, 1, false); 2062 llvm::Value* one = llvm::ConstantInt::get(llvm::Type::Int32Ty, 1, false);
2005 elem* u = e1->toElem(p); 2133 elem* u = e1->toElem(p);
2006 2134
2007 llvm::Value* b = LLVM_DtoBoolean(u->getValue()); 2135 llvm::Value* b = LLVM_DtoBoolean(u->getValue());
2008 2136
2009 llvm::Value* zero = llvm::ConstantInt::get(llvm::Type::Int1Ty, 0, true); 2137 llvm::Value* zero = llvm::ConstantInt::get(llvm::Type::Int1Ty, 0, true);
2010 e->val = new llvm::ICmpInst(llvm::ICmpInst::ICMP_EQ,b,zero,"tmp",p->scopebb()); 2138 e->val = p->ir->CreateICmpEQ(b,zero);
2139 //e->val = new llvm::ICmpInst(llvm::ICmpInst::ICMP_EQ,b,zero,"tmp",p->scopebb());
2011 e->type = elem::VAL; 2140 e->type = elem::VAL;
2012 2141
2013 delete u; 2142 delete u;
2014 2143
2015 return e; 2144 return e;
2149 LOG_SCOPE; 2278 LOG_SCOPE;
2150 2279
2151 llvm::Value* loca = llvm::ConstantInt::get(llvm::Type::Int32Ty, loc.linnum, false); 2280 llvm::Value* loca = llvm::ConstantInt::get(llvm::Type::Int32Ty, loc.linnum, false);
2152 LLVM_DtoAssert(llvm::ConstantInt::getFalse(), loca, NULL); 2281 LLVM_DtoAssert(llvm::ConstantInt::getFalse(), loca, NULL);
2153 2282
2154 //new llvm::UnreachableInst(p->scopebb()); 2283 new llvm::UnreachableInst(p->scopebb());
2155 return 0; 2284 return 0;
2156 } 2285 }
2157 2286
2158 ////////////////////////////////////////////////////////////////////////////////////////// 2287 //////////////////////////////////////////////////////////////////////////////////////////
2159 2288
2303 elem* e = new elem; 2432 elem* e = new elem;
2304 elem* l = e1->toElem(p); 2433 elem* l = e1->toElem(p);
2305 llvm::Value* val = l->getValue(); 2434 llvm::Value* val = l->getValue();
2306 delete l; 2435 delete l;
2307 2436
2437 Type* t = LLVM_DtoDType(type);
2438
2308 llvm::Value* zero = 0; 2439 llvm::Value* zero = 0;
2309 if (type->isintegral()) 2440 if (t->isintegral())
2310 zero = llvm::ConstantInt::get(val->getType(), 0, true); 2441 zero = llvm::ConstantInt::get(val->getType(), 0, true);
2311 else if (type->isfloating()) { 2442 else if (t->isfloating()) {
2312 if (type->ty == Tfloat32) 2443 if (t->ty == Tfloat32)
2313 zero = llvm::ConstantFP::get(val->getType(), float(0)); 2444 zero = llvm::ConstantFP::get(val->getType(), float(0));
2314 else if (type->ty == Tfloat64 || type->ty == Tfloat80) 2445 else if (t->ty == Tfloat64 || t->ty == Tfloat80)
2315 zero = llvm::ConstantFP::get(val->getType(), double(0)); 2446 zero = llvm::ConstantFP::get(val->getType(), double(0));
2316 else 2447 else
2317 assert(0); 2448 assert(0);
2318 } 2449 }
2319 else 2450 else
2330 elem* CatExp::toElem(IRState* p) 2461 elem* CatExp::toElem(IRState* p)
2331 { 2462 {
2332 Logger::print("CatExp::toElem: %s | %s\n", toChars(), type->toChars()); 2463 Logger::print("CatExp::toElem: %s | %s\n", toChars(), type->toChars());
2333 LOG_SCOPE; 2464 LOG_SCOPE;
2334 2465
2335 assert(0 && "array concatenation is not yet implemented"); 2466 assert(0 && "array cat is not yet implemented");
2336 2467
2337 elem* lhs = e1->toElem(p); 2468 elem* lhs = e1->toElem(p);
2338 elem* rhs = e2->toElem(p); 2469 elem* rhs = e2->toElem(p);
2339 2470
2340 // determine new size 2471 // determine new size
2341 2472
2342 delete lhs; 2473 delete lhs;
2343 delete rhs; 2474 delete rhs;
2344 2475
2345 return 0; 2476 return 0;
2477 }
2478
2479 //////////////////////////////////////////////////////////////////////////////////////////
2480
2481 elem* CatAssignExp::toElem(IRState* p)
2482 {
2483 Logger::print("CatAssignExp::toElem: %s | %s\n", toChars(), type->toChars());
2484 LOG_SCOPE;
2485
2486 elem* l = e1->toElem(p);
2487 assert(l->mem);
2488
2489 Type* e1type = LLVM_DtoDType(e1->type);
2490 Type* elemtype = LLVM_DtoDType(e1type->next);
2491 Type* e2type = LLVM_DtoDType(e2->type);
2492
2493 if (e2type == elemtype) {
2494 LLVM_DtoCatArrayElement(l->mem,e2);
2495 }
2496 else
2497 assert(0 && "only one element at a time right now");
2498
2499 return 0;
2500 }
2501
2502 //////////////////////////////////////////////////////////////////////////////////////////
2503
2504 elem* ArrayLiteralExp::toElem(IRState* p)
2505 {
2506 Logger::print("ArrayLiteralExp::toElem: %s | %s\n", toChars(), type->toChars());
2507 LOG_SCOPE;
2508
2509 const llvm::Type* t = LLVM_DtoType(type);
2510 Logger::cout() << "array literal has llvm type: " << *t << '\n';
2511
2512 llvm::Value* mem = 0;
2513 if (p->lvals.empty()) {
2514 assert(LLVM_DtoDType(type)->ty == Tsarray);
2515 mem = new llvm::AllocaInst(t,"tmparrayliteral",p->topallocapoint());
2516 }
2517 else {
2518 mem = p->toplval();
2519 if (!llvm::isa<llvm::PointerType>(mem->getType()) ||
2520 !llvm::isa<llvm::ArrayType>(mem->getType()->getContainedType(0)))
2521 {
2522 error("TODO array literals can currently only be used to initialise static arrays");
2523 fatal();
2524 }
2525 }
2526
2527 for (unsigned i=0; i<elements->dim; ++i)
2528 {
2529 Expression* expr = (Expression*)elements->data[i];
2530 llvm::Value* elemAddr = LLVM_DtoGEPi(mem,0,i,"tmp",p->scopebb());
2531 elem* e = expr->toElem(p);
2532 new llvm::StoreInst(e->getValue(), elemAddr, p->scopebb());
2533 }
2534
2535 elem* e = new elem;
2536 e->mem = mem;
2537 e->type = elem::VAL;
2538 e->inplace = true;
2539
2540 return e;
2541 }
2542
2543 //////////////////////////////////////////////////////////////////////////////////////////
2544
2545 llvm::Constant* ArrayLiteralExp::toConstElem(IRState* p)
2546 {
2547 Logger::print("ArrayLiteralExp::toConstElem: %s | %s\n", toChars(), type->toChars());
2548 LOG_SCOPE;
2549
2550 const llvm::Type* t = LLVM_DtoType(type);
2551 Logger::cout() << "array literal has llvm type: " << *t << '\n';
2552 assert(llvm::isa<llvm::ArrayType>(t));
2553 const llvm::ArrayType* arrtype = llvm::cast<llvm::ArrayType>(t);
2554
2555 assert(arrtype->getNumElements() == elements->dim);
2556 std::vector<llvm::Constant*> vals(elements->dim, NULL);
2557 for (unsigned i=0; i<elements->dim; ++i)
2558 {
2559 Expression* expr = (Expression*)elements->data[i];
2560 vals[i] = expr->toConstElem(p);
2561 }
2562
2563 return llvm::ConstantArray::get(arrtype, vals);
2346 } 2564 }
2347 2565
2348 ////////////////////////////////////////////////////////////////////////////////////////// 2566 //////////////////////////////////////////////////////////////////////////////////////////
2349 2567
2350 #define STUB(x) elem *x::toElem(IRState * p) {error("Exp type "#x" not implemented: %s", toChars()); fatal(); return 0; } 2568 #define STUB(x) elem *x::toElem(IRState * p) {error("Exp type "#x" not implemented: %s", toChars()); fatal(); return 0; }
2372 //STUB(MulExp); 2590 //STUB(MulExp);
2373 //STUB(MulAssignExp); 2591 //STUB(MulAssignExp);
2374 //STUB(ModExp); 2592 //STUB(ModExp);
2375 //STUB(ModAssignExp); 2593 //STUB(ModAssignExp);
2376 //STUB(CatExp); 2594 //STUB(CatExp);
2377 STUB(CatAssignExp); 2595 //STUB(CatAssignExp);
2378 //STUB(AddExp); 2596 //STUB(AddExp);
2379 //STUB(AddAssignExp); 2597 //STUB(AddAssignExp);
2380 STUB(Expression); 2598 STUB(Expression);
2381 //STUB(MinExp); 2599 //STUB(MinExp);
2382 //STUB(MinAssignExp); 2600 //STUB(MinAssignExp);
2415 //STUB(IndexExp); 2633 //STUB(IndexExp);
2416 //STUB(CommaExp); 2634 //STUB(CommaExp);
2417 //STUB(ArrayLengthExp); 2635 //STUB(ArrayLengthExp);
2418 //STUB(HaltExp); 2636 //STUB(HaltExp);
2419 STUB(RemoveExp); 2637 STUB(RemoveExp);
2420 STUB(ArrayLiteralExp); 2638 //STUB(ArrayLiteralExp);
2421 STUB(AssocArrayLiteralExp); 2639 STUB(AssocArrayLiteralExp);
2422 //STUB(StructLiteralExp); 2640 //STUB(StructLiteralExp);
2423 2641
2642 #define CONSTSTUB(x) llvm::Constant* x::toConstElem(IRState * p) {error("const Exp type "#x" not implemented: '%s' type: '%s'", toChars(), type->toChars()); assert(0); fatal(); return NULL; }
2643 CONSTSTUB(Expression);
2644 //CONSTSTUB(IntegerExp);
2645 //CONSTSTUB(RealExp);
2646 //CONSTSTUB(NullExp);
2647 //CONSTSTUB(StringExp);
2648 //CONSTSTUB(VarExp);
2649 //CONSTSTUB(ArrayLiteralExp);
2650 CONSTSTUB(AssocArrayLiteralExp);
2651 //CONSTSTUB(StructLiteralExp);
2652
2424 unsigned Type::totym() { return 0; } 2653 unsigned Type::totym() { return 0; }
2425 2654
2426 type * Type::toCtype() 2655 type * Type::toCtype()
2427 { 2656 {
2428 assert(0); 2657 assert(0);