mirror of
https://github.com/ldc-developers/ldc.git
synced 2025-05-01 15:40:55 +03:00
Error message for calling a function with a missing 'this' arg.
This commit is contained in:
parent
d9f85de2a1
commit
3db56c7a17
4 changed files with 37 additions and 28 deletions
|
@ -798,7 +798,7 @@ DValue* DtoNewClass(TypeClass* tc, NewExp* newexp)
|
||||||
{
|
{
|
||||||
DtoForceDeclareDsymbol(newexp->allocator);
|
DtoForceDeclareDsymbol(newexp->allocator);
|
||||||
DFuncValue dfn(newexp->allocator, newexp->allocator->ir.irFunc->func);
|
DFuncValue dfn(newexp->allocator, newexp->allocator->ir.irFunc->func);
|
||||||
DValue* res = DtoCallFunction(NULL, &dfn, newexp->newargs);
|
DValue* res = DtoCallFunction(newexp->loc, NULL, &dfn, newexp->newargs);
|
||||||
mem = DtoBitCast(res->getRVal(), DtoType(tc), ".newclass_custom");
|
mem = DtoBitCast(res->getRVal(), DtoType(tc), ".newclass_custom");
|
||||||
}
|
}
|
||||||
// default allocator
|
// default allocator
|
||||||
|
@ -852,7 +852,7 @@ DValue* DtoNewClass(TypeClass* tc, NewExp* newexp)
|
||||||
assert(newexp->arguments != NULL);
|
assert(newexp->arguments != NULL);
|
||||||
DtoForceDeclareDsymbol(newexp->member);
|
DtoForceDeclareDsymbol(newexp->member);
|
||||||
DFuncValue dfn(newexp->member, newexp->member->ir.irFunc->func, mem);
|
DFuncValue dfn(newexp->member, newexp->member->ir.irFunc->func, mem);
|
||||||
return DtoCallFunction(tc, &dfn, newexp->arguments);
|
return DtoCallFunction(newexp->loc, tc, &dfn, newexp->arguments);
|
||||||
}
|
}
|
||||||
|
|
||||||
// return default constructed class
|
// return default constructed class
|
||||||
|
|
|
@ -118,6 +118,6 @@ const LLFunctionType* DtoExtractFunctionType(const LLType* type);
|
||||||
void DtoBuildDVarArgList(std::vector<LLValue*>& args, llvm::PAListPtr& palist, TypeFunction* tf, Expressions* arguments, size_t argidx);
|
void DtoBuildDVarArgList(std::vector<LLValue*>& args, llvm::PAListPtr& palist, TypeFunction* tf, Expressions* arguments, size_t argidx);
|
||||||
|
|
||||||
///
|
///
|
||||||
DValue* DtoCallFunction(Type* resulttype, DValue* fnval, Expressions* arguments);
|
DValue* DtoCallFunction(Loc& loc, Type* resulttype, DValue* fnval, Expressions* arguments);
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -180,7 +180,7 @@ void DtoBuildDVarArgList(std::vector<LLValue*>& args, llvm::PAListPtr& palist, T
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
DValue* DtoCallFunction(Type* resulttype, DValue* fnval, Expressions* arguments)
|
DValue* DtoCallFunction(Loc& loc, Type* resulttype, DValue* fnval, Expressions* arguments)
|
||||||
{
|
{
|
||||||
// the callee D type
|
// the callee D type
|
||||||
Type* calleeType = fnval->getType();
|
Type* calleeType = fnval->getType();
|
||||||
|
@ -224,31 +224,40 @@ DValue* DtoCallFunction(Type* resulttype, DValue* fnval, Expressions* arguments)
|
||||||
args.push_back(retvar);
|
args.push_back(retvar);
|
||||||
}
|
}
|
||||||
|
|
||||||
// then comes the 'this' argument
|
// then comes a context argument...
|
||||||
if (dfnval && dfnval->vthis)
|
if(usesthis || delegatecall || nestedcall)
|
||||||
{
|
{
|
||||||
LLValue* thisarg = DtoBitCast(dfnval->vthis, argiter->get());
|
// ... which can be a 'this' argument
|
||||||
++argiter;
|
if (dfnval && dfnval->vthis)
|
||||||
args.push_back(thisarg);
|
{
|
||||||
}
|
LLValue* thisarg = DtoBitCast(dfnval->vthis, argiter->get());
|
||||||
// or a delegate context arg
|
++argiter;
|
||||||
else if (delegatecall)
|
args.push_back(thisarg);
|
||||||
{
|
}
|
||||||
LLValue* ctxarg = DtoLoad(DtoGEPi(fnval->getRVal(), 0,0));
|
// ... or a delegate context arg
|
||||||
assert(ctxarg->getType() == argiter->get());
|
else if (delegatecall)
|
||||||
++argiter;
|
{
|
||||||
args.push_back(ctxarg);
|
LLValue* ctxarg = DtoLoad(DtoGEPi(fnval->getRVal(), 0,0));
|
||||||
}
|
assert(ctxarg->getType() == argiter->get());
|
||||||
// or a nested function context arg
|
++argiter;
|
||||||
else if (nestedcall)
|
args.push_back(ctxarg);
|
||||||
{
|
}
|
||||||
LLValue* contextptr = DtoNestedContext(dfnval->func->toParent2()->isFuncDeclaration());
|
// ... or a nested function context arg
|
||||||
if (!contextptr)
|
else if (nestedcall)
|
||||||
contextptr = getNullPtr(getVoidPtrType());
|
{
|
||||||
|
LLValue* contextptr = DtoNestedContext(dfnval->func->toParent2()->isFuncDeclaration());
|
||||||
|
if (!contextptr)
|
||||||
|
contextptr = getNullPtr(getVoidPtrType());
|
||||||
|
else
|
||||||
|
contextptr = DtoBitCast(contextptr, getVoidPtrType());
|
||||||
|
++argiter;
|
||||||
|
args.push_back(contextptr);
|
||||||
|
}
|
||||||
else
|
else
|
||||||
contextptr = DtoBitCast(contextptr, getVoidPtrType());
|
{
|
||||||
++argiter;
|
error(loc, "Context argument required but none given");
|
||||||
args.push_back(contextptr);
|
fatal();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// handle the rest of the arguments based on param passing style
|
// handle the rest of the arguments based on param passing style
|
||||||
|
|
|
@ -886,7 +886,7 @@ DValue* CallExp::toElem(IRState* p)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return DtoCallFunction(type, fnval, arguments);
|
return DtoCallFunction(loc, type, fnval, arguments);
|
||||||
}
|
}
|
||||||
|
|
||||||
//////////////////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue