diff --git a/gen/llvmhelpers.cpp b/gen/llvmhelpers.cpp index e9c6ec2fb8..dacd08969f 100644 --- a/gen/llvmhelpers.cpp +++ b/gen/llvmhelpers.cpp @@ -1600,7 +1600,6 @@ DValue *DtoSymbolAddress(Loc &loc, Type *type, Declaration *decl) { if (vd->storage_class & STClazy) { Logger::println("lazy parameter"); assert(type->ty == Tdelegate); - return new DVarValue(type, getIrValue(vd)); } assert(!isSpecialRefVar(vd) && "Code not expected to handle special " "ref vars, although it can easily be " diff --git a/gen/structs.cpp b/gen/structs.cpp index 2a938ebd55..62ff8b50f5 100644 --- a/gen/structs.cpp +++ b/gen/structs.cpp @@ -168,7 +168,7 @@ void DtoPaddedStruct(Type *dty, LLValue *v, LLValue *lval) { // Nested structs are the only members that can contain padding DtoPaddedStruct(fields[i]->type, fieldval, fieldptr); } else { - DtoStore(fieldval, fieldptr); + DtoStoreZextI8(fieldval, fieldptr); } } } diff --git a/gen/tocall.cpp b/gen/tocall.cpp index 21b4bb5296..bb2d2d4515 100644 --- a/gen/tocall.cpp +++ b/gen/tocall.cpp @@ -882,45 +882,21 @@ DValue *DtoCallFunction(Loc &loc, Type *resulttype, DValue *fnval, : 0); LLValue *retllval = (irFty.arg_sret ? args[sretArgIndex] : call.getInstruction()); + bool retValIsLVal = (tf->isref && returnTy != Tvoid) || (irFty.arg_sret != nullptr); - // Hack around LDC assuming structs and static arrays are in memory: - // If the function returns a struct or a static array, and the return - // value is not a pointer to a struct or a static array, store it to - // a stack slot before continuing. - bool storeReturnValueOnStack = - (returnTy == Tstruct && !isaPointer(retllval)) || - (returnTy == Tsarray && isaArray(retllval)); - - bool retValIsAlloca = false; - - // ignore ABI for intrinsics - const bool intrinsic = - (dfnval && dfnval->func && DtoIsIntrinsic(dfnval->func)); - if (!intrinsic && !irFty.arg_sret) { - // do ABI specific return value fixups - if (storeReturnValueOnStack) { - Logger::println("Storing return value to stack slot"); + if (!retValIsLVal) { + // let the ABI transform the return value back + if (DtoIsInMemoryOnly(returntype)) { retllval = irFty.getRetLVal(returntype, retllval); - retValIsAlloca = true; - storeReturnValueOnStack = false; + retValIsLVal = true; } else { retllval = irFty.getRetRVal(returntype, retllval); - storeReturnValueOnStack = - (returnTy == Tstruct && !isaPointer(retllval)) || - (returnTy == Tsarray && isaArray(retllval)); } } - if (storeReturnValueOnStack) { - Logger::println("Storing return value to stack slot"); - retllval = DtoAllocaDump(retllval, returntype); - retValIsAlloca = true; - } - // repaint the type if necessary Type *rbase = stripModifiers(resulttype->toBasetype(), true); Type *nextbase = stripModifiers(returntype->toBasetype(), true); - bool retinptr = irFty.arg_sret; if (!rbase->equals(nextbase)) { IF_LOG Logger::println("repainting return value from '%s' to '%s'", returntype->toChars(), rbase->toChars()); @@ -958,7 +934,7 @@ DValue *DtoCallFunction(Loc &loc, Type *resulttype, DValue *fnval, LLValue *val = DtoInsertValue(llvm::UndefValue::get(DtoType(rbase)), retllval, 0); retllval = DtoAllocaDump(val, rbase, ".aalvaluetmp"); - retinptr = true; + retValIsLVal = true; break; } // Fall through. @@ -1033,10 +1009,7 @@ DValue *DtoCallFunction(Loc &loc, Type *resulttype, DValue *fnval, return new DVarValue(resulttype, dfnval->vthis); } - // if we are returning through a pointer arg - // or if we are returning a reference - // make sure we provide a lvalue back! - if (retinptr || (tf->isref && returnTy != Tvoid) || retValIsAlloca) { + if (retValIsLVal) { return new DVarValue(resulttype, retllval); }