SemaTemplateInstantiateDecl.cpp revision 615c5d4674355ba830b9978f462ca7a8c5d15f85
1//===--- SemaTemplateInstantiateDecl.cpp - C++ Template Decl Instantiation ===/ 2// 3// The LLVM Compiler Infrastructure 4// 5// This file is distributed under the University of Illinois Open Source 6// License. See LICENSE.TXT for details. 7//===----------------------------------------------------------------------===/ 8// 9// This file implements C++ template instantiation for declarations. 10// 11//===----------------------------------------------------------------------===/ 12#include "Sema.h" 13#include "clang/AST/ASTContext.h" 14#include "clang/AST/DeclTemplate.h" 15#include "clang/AST/DeclVisitor.h" 16#include "clang/AST/Expr.h" 17#include "llvm/Support/Compiler.h" 18 19using namespace clang; 20 21namespace { 22 class VISIBILITY_HIDDEN TemplateDeclInstantiator 23 : public DeclVisitor<TemplateDeclInstantiator, Decl *> 24 { 25 Sema &SemaRef; 26 DeclContext *Owner; 27 const TemplateArgument *TemplateArgs; 28 unsigned NumTemplateArgs; 29 30 public: 31 typedef Sema::OwningExprResult OwningExprResult; 32 33 TemplateDeclInstantiator(Sema &SemaRef, DeclContext *Owner, 34 const TemplateArgument *TemplateArgs, 35 unsigned NumTemplateArgs) 36 : SemaRef(SemaRef), Owner(Owner), TemplateArgs(TemplateArgs), 37 NumTemplateArgs(NumTemplateArgs) { } 38 39 // FIXME: Once we get closer to completion, replace these 40 // manually-written declarations with automatically-generated ones 41 // from clang/AST/DeclNodes.def. 42 Decl *VisitTypedefDecl(TypedefDecl *D); 43 Decl *VisitFieldDecl(FieldDecl *D); 44 Decl *VisitStaticAssertDecl(StaticAssertDecl *D); 45 Decl *VisitEnumDecl(EnumDecl *D); 46 Decl *VisitCXXMethodDecl(CXXMethodDecl *D); 47 Decl *VisitCXXConstructorDecl(CXXConstructorDecl *D); 48 Decl *VisitCXXDestructorDecl(CXXDestructorDecl *D); 49 Decl *VisitParmVarDecl(ParmVarDecl *D); 50 Decl *VisitOriginalParmVarDecl(OriginalParmVarDecl *D); 51 52 // Base case. FIXME: Remove once we can instantiate everything. 53 Decl *VisitDecl(Decl *) { 54 return 0; 55 } 56 57 // Helper functions for instantiating methods. 58 QualType InstantiateFunctionType(FunctionDecl *D, 59 llvm::SmallVectorImpl<ParmVarDecl *> &Params); 60 bool InitMethodInstantiation(CXXMethodDecl *New, CXXMethodDecl *Tmpl); 61 }; 62} 63 64Decl *TemplateDeclInstantiator::VisitTypedefDecl(TypedefDecl *D) { 65 bool Invalid = false; 66 QualType T = D->getUnderlyingType(); 67 if (T->isDependentType()) { 68 T = SemaRef.InstantiateType(T, TemplateArgs, NumTemplateArgs, 69 D->getLocation(), 70 D->getDeclName()); 71 if (T.isNull()) { 72 Invalid = true; 73 T = SemaRef.Context.IntTy; 74 } 75 } 76 77 // Create the new typedef 78 TypedefDecl *Typedef 79 = TypedefDecl::Create(SemaRef.Context, Owner, D->getLocation(), 80 D->getIdentifier(), T); 81 if (Invalid) 82 Typedef->setInvalidDecl(); 83 84 Owner->addDecl(Typedef); 85 return Typedef; 86} 87 88Decl *TemplateDeclInstantiator::VisitFieldDecl(FieldDecl *D) { 89 bool Invalid = false; 90 QualType T = D->getType(); 91 if (T->isDependentType()) { 92 T = SemaRef.InstantiateType(T, TemplateArgs, NumTemplateArgs, 93 D->getLocation(), 94 D->getDeclName()); 95 if (!T.isNull() && T->isFunctionType()) { 96 // C++ [temp.arg.type]p3: 97 // If a declaration acquires a function type through a type 98 // dependent on a template-parameter and this causes a 99 // declaration that does not use the syntactic form of a 100 // function declarator to have function type, the program is 101 // ill-formed. 102 SemaRef.Diag(D->getLocation(), diag::err_field_instantiates_to_function) 103 << T; 104 T = QualType(); 105 Invalid = true; 106 } 107 } 108 109 Expr *BitWidth = D->getBitWidth(); 110 if (Invalid) 111 BitWidth = 0; 112 else if (BitWidth) { 113 OwningExprResult InstantiatedBitWidth 114 = SemaRef.InstantiateExpr(BitWidth, TemplateArgs, NumTemplateArgs); 115 if (InstantiatedBitWidth.isInvalid()) { 116 Invalid = true; 117 BitWidth = 0; 118 } else 119 BitWidth = (Expr *)InstantiatedBitWidth.release(); 120 } 121 122 FieldDecl *Field = SemaRef.CheckFieldDecl(D->getDeclName(), T, 123 cast<RecordDecl>(Owner), 124 D->getLocation(), 125 D->isMutable(), 126 BitWidth, 127 D->getAccess(), 128 0); 129 if (Field) { 130 if (Invalid) 131 Field->setInvalidDecl(); 132 133 Owner->addDecl(Field); 134 } 135 136 return Field; 137} 138 139Decl *TemplateDeclInstantiator::VisitStaticAssertDecl(StaticAssertDecl *D) { 140 Expr *AssertExpr = D->getAssertExpr(); 141 142 OwningExprResult InstantiatedAssertExpr 143 = SemaRef.InstantiateExpr(AssertExpr, TemplateArgs, NumTemplateArgs); 144 if (InstantiatedAssertExpr.isInvalid()) 145 return 0; 146 147 OwningExprResult Message = SemaRef.Clone(D->getMessage()); 148 Decl *StaticAssert 149 = (Decl *)SemaRef.ActOnStaticAssertDeclaration(D->getLocation(), 150 move(InstantiatedAssertExpr), 151 move(Message)); 152 return StaticAssert; 153} 154 155Decl *TemplateDeclInstantiator::VisitEnumDecl(EnumDecl *D) { 156 EnumDecl *Enum = EnumDecl::Create(SemaRef.Context, Owner, 157 D->getLocation(), D->getIdentifier(), 158 /*PrevDecl=*/0); 159 Owner->addDecl(Enum); 160 Enum->startDefinition(); 161 162 llvm::SmallVector<Sema::DeclTy *, 16> Enumerators; 163 164 EnumConstantDecl *LastEnumConst = 0; 165 for (EnumDecl::enumerator_iterator EC = D->enumerator_begin(), 166 ECEnd = D->enumerator_end(); 167 EC != ECEnd; ++EC) { 168 // The specified value for the enumerator. 169 OwningExprResult Value = SemaRef.Owned((Expr *)0); 170 if (Expr *UninstValue = EC->getInitExpr()) 171 Value = SemaRef.InstantiateExpr(UninstValue, 172 TemplateArgs, NumTemplateArgs); 173 174 // Drop the initial value and continue. 175 bool isInvalid = false; 176 if (Value.isInvalid()) { 177 Value = SemaRef.Owned((Expr *)0); 178 isInvalid = true; 179 } 180 181 EnumConstantDecl *EnumConst 182 = SemaRef.CheckEnumConstant(Enum, LastEnumConst, 183 EC->getLocation(), EC->getIdentifier(), 184 move(Value)); 185 186 if (isInvalid) { 187 if (EnumConst) 188 EnumConst->setInvalidDecl(); 189 Enum->setInvalidDecl(); 190 } 191 192 if (EnumConst) { 193 Enum->addDecl(EnumConst); 194 Enumerators.push_back(EnumConst); 195 LastEnumConst = EnumConst; 196 } 197 } 198 199 SemaRef.ActOnEnumBody(Enum->getLocation(), Enum, 200 &Enumerators[0], Enumerators.size()); 201 202 return Enum; 203} 204 205Decl *TemplateDeclInstantiator::VisitCXXMethodDecl(CXXMethodDecl *D) { 206 // Only handle actual methods; we'll deal with constructors, 207 // destructors, etc. separately. 208 if (D->getKind() != Decl::CXXMethod) 209 return 0; 210 211 llvm::SmallVector<ParmVarDecl *, 16> Params; 212 QualType T = InstantiateFunctionType(D, Params); 213 if (T.isNull()) 214 return 0; 215 216 // Build the instantiated method declaration. 217 CXXRecordDecl *Record = cast<CXXRecordDecl>(Owner); 218 CXXMethodDecl *Method 219 = CXXMethodDecl::Create(SemaRef.Context, Record, D->getLocation(), 220 D->getDeclName(), T, D->isStatic(), 221 D->isInline()); 222 223 // Attach the parameters 224 for (unsigned P = 0; P < Params.size(); ++P) 225 Params[P]->setOwningFunction(Method); 226 Method->setParams(SemaRef.Context, &Params[0], Params.size()); 227 228 if (InitMethodInstantiation(Method, D)) 229 Method->setInvalidDecl(); 230 231 NamedDecl *PrevDecl 232 = SemaRef.LookupQualifiedName(Owner, Method->getDeclName(), 233 Sema::LookupOrdinaryName, true); 234 // In C++, the previous declaration we find might be a tag type 235 // (class or enum). In this case, the new declaration will hide the 236 // tag type. Note that this does does not apply if we're declaring a 237 // typedef (C++ [dcl.typedef]p4). 238 if (PrevDecl && PrevDecl->getIdentifierNamespace() == Decl::IDNS_Tag) 239 PrevDecl = 0; 240 bool Redeclaration = false; 241 bool OverloadableAttrRequired = false; 242 if (SemaRef.CheckFunctionDeclaration(Method, PrevDecl, Redeclaration, 243 /*FIXME:*/OverloadableAttrRequired)) 244 Method->setInvalidDecl(); 245 246 if (!Method->isInvalidDecl() || !PrevDecl) 247 Owner->addDecl(Method); 248 return Method; 249} 250 251Decl *TemplateDeclInstantiator::VisitCXXConstructorDecl(CXXConstructorDecl *D) { 252 llvm::SmallVector<ParmVarDecl *, 16> Params; 253 QualType T = InstantiateFunctionType(D, Params); 254 if (T.isNull()) 255 return 0; 256 257 // Build the instantiated method declaration. 258 CXXRecordDecl *Record = cast<CXXRecordDecl>(Owner); 259 QualType ClassTy = SemaRef.Context.getTypeDeclType(Record); 260 DeclarationName Name 261 = SemaRef.Context.DeclarationNames.getCXXConstructorName(ClassTy); 262 CXXConstructorDecl *Constructor 263 = CXXConstructorDecl::Create(SemaRef.Context, Record, D->getLocation(), 264 Name, T, D->isExplicit(), D->isInline(), 265 false); 266 267 // Attach the parameters 268 for (unsigned P = 0; P < Params.size(); ++P) 269 Params[P]->setOwningFunction(Constructor); 270 Constructor->setParams(SemaRef.Context, &Params[0], Params.size()); 271 272 if (InitMethodInstantiation(Constructor, D)) 273 Constructor->setInvalidDecl(); 274 275 NamedDecl *PrevDecl 276 = SemaRef.LookupQualifiedName(Owner, Name, Sema::LookupOrdinaryName, true); 277 278 // In C++, the previous declaration we find might be a tag type 279 // (class or enum). In this case, the new declaration will hide the 280 // tag type. Note that this does does not apply if we're declaring a 281 // typedef (C++ [dcl.typedef]p4). 282 if (PrevDecl && PrevDecl->getIdentifierNamespace() == Decl::IDNS_Tag) 283 PrevDecl = 0; 284 bool Redeclaration = false; 285 bool OverloadableAttrRequired = false; 286 if (SemaRef.CheckFunctionDeclaration(Constructor, PrevDecl, Redeclaration, 287 /*FIXME:*/OverloadableAttrRequired)) 288 Constructor->setInvalidDecl(); 289 290 if (!Constructor->isInvalidDecl()) 291 Owner->addDecl(Constructor); 292 return Constructor; 293} 294 295Decl *TemplateDeclInstantiator::VisitCXXDestructorDecl(CXXDestructorDecl *D) { 296 llvm::SmallVector<ParmVarDecl *, 16> Params; 297 QualType T = InstantiateFunctionType(D, Params); 298 if (T.isNull()) 299 return 0; 300 assert(Params.size() == 0 && "Destructor with parameters?"); 301 302 // Build the instantiated destructor declaration. 303 CXXRecordDecl *Record = cast<CXXRecordDecl>(Owner); 304 QualType ClassTy = SemaRef.Context.getTypeDeclType(Record); 305 CXXDestructorDecl *Destructor 306 = CXXDestructorDecl::Create(SemaRef.Context, Record, 307 D->getLocation(), 308 SemaRef.Context.DeclarationNames.getCXXDestructorName(ClassTy), 309 T, D->isInline(), false); 310 if (InitMethodInstantiation(Destructor, D)) 311 Destructor->setInvalidDecl(); 312 313 bool Redeclaration = false; 314 bool OverloadableAttrRequired = false; 315 NamedDecl *PrevDecl = 0; 316 if (SemaRef.CheckFunctionDeclaration(Destructor, PrevDecl, Redeclaration, 317 /*FIXME:*/OverloadableAttrRequired)) 318 Destructor->setInvalidDecl(); 319 Owner->addDecl(Destructor); 320 return Destructor; 321} 322 323Decl *TemplateDeclInstantiator::VisitParmVarDecl(ParmVarDecl *D) { 324 QualType OrigT = SemaRef.InstantiateType(D->getOriginalType(), TemplateArgs, 325 NumTemplateArgs, D->getLocation(), 326 D->getDeclName()); 327 if (OrigT.isNull()) 328 return 0; 329 330 QualType T = SemaRef.adjustParameterType(OrigT); 331 332 if (D->getDefaultArg()) { 333 // FIXME: Leave a marker for "uninstantiated" default 334 // arguments. They only get instantiated on demand at the call 335 // site. 336 unsigned DiagID = SemaRef.Diags.getCustomDiagID(Diagnostic::Warning, 337 "sorry, dropping default argument during template instantiation"); 338 SemaRef.Diag(D->getDefaultArg()->getSourceRange().getBegin(), DiagID) 339 << D->getDefaultArg()->getSourceRange(); 340 } 341 342 // Allocate the parameter 343 ParmVarDecl *Param = 0; 344 if (T == OrigT) 345 Param = ParmVarDecl::Create(SemaRef.Context, Owner, D->getLocation(), 346 D->getIdentifier(), T, D->getStorageClass(), 347 0); 348 else 349 Param = OriginalParmVarDecl::Create(SemaRef.Context, Owner, 350 D->getLocation(), D->getIdentifier(), 351 T, OrigT, D->getStorageClass(), 0); 352 353 // Note: we don't try to instantiate function parameters until after 354 // we've instantiated the function's type. Therefore, we don't have 355 // to check for 'void' parameter types here. 356 return Param; 357} 358 359Decl * 360TemplateDeclInstantiator::VisitOriginalParmVarDecl(OriginalParmVarDecl *D) { 361 // Since parameter types can decay either before or after 362 // instantiation, we simply treat OriginalParmVarDecls as 363 // ParmVarDecls the same way, and create one or the other depending 364 // on what happens after template instantiation. 365 return VisitParmVarDecl(D); 366} 367 368Decl *Sema::InstantiateDecl(Decl *D, DeclContext *Owner, 369 const TemplateArgument *TemplateArgs, 370 unsigned NumTemplateArgs) { 371 TemplateDeclInstantiator Instantiator(*this, Owner, TemplateArgs, 372 NumTemplateArgs); 373 return Instantiator.Visit(D); 374} 375 376/// \brief Instantiates the type of the given function, including 377/// instantiating all of the function parameters. 378/// 379/// \param D The function that we will be instantiated 380/// 381/// \param Params the instantiated parameter declarations 382 383/// \returns the instantiated function's type if successfull, a NULL 384/// type if there was an error. 385QualType 386TemplateDeclInstantiator::InstantiateFunctionType(FunctionDecl *D, 387 llvm::SmallVectorImpl<ParmVarDecl *> &Params) { 388 bool InvalidDecl = false; 389 390 // Instantiate the function parameters 391 TemplateDeclInstantiator ParamInstantiator(SemaRef, 0, 392 TemplateArgs, NumTemplateArgs); 393 llvm::SmallVector<QualType, 16> ParamTys; 394 for (FunctionDecl::param_iterator P = D->param_begin(), 395 PEnd = D->param_end(); 396 P != PEnd; ++P) { 397 if (ParmVarDecl *PInst = (ParmVarDecl *)ParamInstantiator.Visit(*P)) { 398 if (PInst->getType()->isVoidType()) { 399 SemaRef.Diag(PInst->getLocation(), diag::err_param_with_void_type); 400 PInst->setInvalidDecl(); 401 } 402 else if (SemaRef.RequireNonAbstractType(PInst->getLocation(), 403 PInst->getType(), 404 diag::err_abstract_type_in_decl, 405 Sema::AbstractParamType)) 406 PInst->setInvalidDecl(); 407 408 Params.push_back(PInst); 409 ParamTys.push_back(PInst->getType()); 410 411 if (PInst->isInvalidDecl()) 412 InvalidDecl = true; 413 } else 414 InvalidDecl = true; 415 } 416 417 // FIXME: Deallocate dead declarations. 418 if (InvalidDecl) 419 return QualType(); 420 421 const FunctionProtoType *Proto = D->getType()->getAsFunctionProtoType(); 422 assert(Proto && "Missing prototype?"); 423 QualType ResultType 424 = SemaRef.InstantiateType(Proto->getResultType(), 425 TemplateArgs, NumTemplateArgs, 426 D->getLocation(), D->getDeclName()); 427 if (ResultType.isNull()) 428 return QualType(); 429 430 return SemaRef.BuildFunctionType(ResultType, &ParamTys[0], ParamTys.size(), 431 Proto->isVariadic(), Proto->getTypeQuals(), 432 D->getLocation(), D->getDeclName()); 433} 434 435/// \brief Initializes common fields of an instantiated method 436/// declaration (New) from the corresponding fields of its template 437/// (Tmpl). 438/// 439/// \returns true if there was an error 440bool 441TemplateDeclInstantiator::InitMethodInstantiation(CXXMethodDecl *New, 442 CXXMethodDecl *Tmpl) { 443 CXXRecordDecl *Record = cast<CXXRecordDecl>(Owner); 444 New->setAccess(Tmpl->getAccess()); 445 if (Tmpl->isVirtual()) { 446 New->setVirtual(); 447 Record->setAggregate(false); 448 Record->setPOD(false); 449 Record->setPolymorphic(true); 450 } 451 if (Tmpl->isDeleted()) 452 New->setDeleted(); 453 if (Tmpl->isPure()) { 454 New->setPure(); 455 Record->setAbstract(true); 456 } 457 458 // FIXME: attributes 459 // FIXME: New needs a pointer to Tmpl 460 return false; 461} 462