forked from OSchip/llvm-project
When instantiating a function that was declared via a typedef, e.g.,
typedef int functype(int, int); functype func; also instantiate the synthesized function parameters for the resulting function declaration. With this change, Boost.Wave builds and passes all of its regression tests. llvm-svn: 103025
This commit is contained in:
parent
a25ee78fc0
commit
c8be95274d
|
@ -495,7 +495,10 @@ CollectRecordFields(const RecordDecl *RD, llvm::DIFile Unit,
|
|||
llvm::DIType
|
||||
CGDebugInfo::getOrCreateMethodType(const CXXMethodDecl *Method,
|
||||
llvm::DIFile Unit) {
|
||||
llvm::DIType FnTy = getOrCreateType(Method->getType(), Unit);
|
||||
llvm::DIType FnTy
|
||||
= getOrCreateType(QualType(Method->getType()->getAs<FunctionProtoType>(),
|
||||
0),
|
||||
Unit);
|
||||
|
||||
// Static methods do not need "this" pointer argument.
|
||||
if (Method->isStatic())
|
||||
|
|
|
@ -3243,8 +3243,10 @@ Sema::ActOnFunctionDeclarator(Scope* S, Declarator& D, DeclContext* DC,
|
|||
for (FunctionProtoType::arg_type_iterator AI = FT->arg_type_begin(),
|
||||
AE = FT->arg_type_end(); AI != AE; ++AI) {
|
||||
ParmVarDecl *Param = ParmVarDecl::Create(Context, NewFD,
|
||||
SourceLocation(), 0,
|
||||
*AI, /*TInfo=*/0,
|
||||
D.getIdentifierLoc(), 0,
|
||||
*AI,
|
||||
Context.getTrivialTypeSourceInfo(*AI,
|
||||
D.getIdentifierLoc()),
|
||||
VarDecl::None,
|
||||
VarDecl::None, 0);
|
||||
Param->setImplicit();
|
||||
|
|
|
@ -3565,8 +3565,8 @@ Sema::ActOnCallExpr(Scope *S, ExprArg fn, SourceLocation LParenLoc,
|
|||
if (BinaryOperator *BO = dyn_cast<BinaryOperator>(NakedFn)) {
|
||||
if (BO->getOpcode() == BinaryOperator::PtrMemD ||
|
||||
BO->getOpcode() == BinaryOperator::PtrMemI) {
|
||||
if (const FunctionProtoType *FPT =
|
||||
dyn_cast<FunctionProtoType>(BO->getType())) {
|
||||
if (const FunctionProtoType *FPT
|
||||
= BO->getType()->getAs<FunctionProtoType>()) {
|
||||
QualType ResultTy = FPT->getResultType().getNonReferenceType();
|
||||
|
||||
ExprOwningPtr<CXXMemberCallExpr>
|
||||
|
|
|
@ -6513,7 +6513,7 @@ Sema::BuildCallToMemberFunction(Scope *S, Expr *MemExprE,
|
|||
MemExpr->setBase(ObjectArg);
|
||||
|
||||
// Convert the rest of the arguments
|
||||
const FunctionProtoType *Proto = cast<FunctionProtoType>(Method->getType());
|
||||
const FunctionProtoType *Proto = Method->getType()->getAs<FunctionProtoType>();
|
||||
if (ConvertArgumentsForCall(&*TheCall, MemExpr, Method, Proto, Args, NumArgs,
|
||||
RParenLoc))
|
||||
return ExprError();
|
||||
|
|
|
@ -1169,6 +1169,27 @@ TemplateDeclInstantiator::VisitCXXMethodDecl(CXXMethodDecl *D,
|
|||
return 0;
|
||||
QualType T = TInfo->getType();
|
||||
|
||||
// \brief If the type of this function is not *directly* a function
|
||||
// type, then we're instantiating the a function that was declared
|
||||
// via a typedef, e.g.,
|
||||
//
|
||||
// typedef int functype(int, int);
|
||||
// functype func;
|
||||
//
|
||||
// In this case, we'll just go instantiate the ParmVarDecls that we
|
||||
// synthesized in the method declaration.
|
||||
if (!isa<FunctionProtoType>(T)) {
|
||||
assert(!Params.size() && "Instantiating type could not yield parameters");
|
||||
for (unsigned I = 0, N = D->getNumParams(); I != N; ++I) {
|
||||
ParmVarDecl *P = SemaRef.SubstParmVarDecl(D->getParamDecl(I),
|
||||
TemplateArgs);
|
||||
if (!P)
|
||||
return 0;
|
||||
|
||||
Params.push_back(P);
|
||||
}
|
||||
}
|
||||
|
||||
NestedNameSpecifier *Qualifier = D->getQualifier();
|
||||
if (Qualifier) {
|
||||
Qualifier = SemaRef.SubstNestedNameSpecifier(Qualifier,
|
||||
|
|
|
@ -120,7 +120,7 @@ extern __typeof (i1) i1;
|
|||
typedef int a();
|
||||
typedef int a2(int*);
|
||||
a x;
|
||||
a2 x2;
|
||||
a2 x2; // expected-note{{passing argument to parameter here}}
|
||||
void test_x() {
|
||||
x(5);
|
||||
x2(5); // expected-warning{{incompatible integer to pointer conversion passing 'int' to parameter of type 'int *'}}
|
||||
|
|
|
@ -76,3 +76,15 @@ namespace PR6990 {
|
|||
{
|
||||
};
|
||||
}
|
||||
|
||||
namespace InstantiateFunctionTypedef {
|
||||
template<typename T>
|
||||
struct X {
|
||||
typedef int functype(int, int);
|
||||
functype func;
|
||||
};
|
||||
|
||||
void f(X<int> x) {
|
||||
(void)x.func(1, 2);
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue