| Reid Spencer | 5f016e2 | 2007-07-11 17:01:13 +0000 | [diff] [blame] | 1 | //===--- Sema.cpp - AST Builder and Semantic Analysis Implementation ------===// | 
 | 2 | // | 
 | 3 | //                     The LLVM Compiler Infrastructure | 
 | 4 | // | 
| Chris Lattner | 0bc735f | 2007-12-29 19:59:25 +0000 | [diff] [blame] | 5 | // This file is distributed under the University of Illinois Open Source | 
 | 6 | // License. See LICENSE.TXT for details. | 
| Reid Spencer | 5f016e2 | 2007-07-11 17:01:13 +0000 | [diff] [blame] | 7 | // | 
 | 8 | //===----------------------------------------------------------------------===// | 
 | 9 | // | 
 | 10 | // This file implements the actions class which performs semantic analysis and | 
 | 11 | // builds an AST out of a parse stream. | 
 | 12 | // | 
 | 13 | //===----------------------------------------------------------------------===// | 
 | 14 |  | 
 | 15 | #include "Sema.h" | 
| Douglas Gregor | b6c8c8b | 2009-04-21 17:11:58 +0000 | [diff] [blame] | 16 | #include "clang/AST/ASTConsumer.h" | 
| Reid Spencer | 5f016e2 | 2007-07-11 17:01:13 +0000 | [diff] [blame] | 17 | #include "clang/AST/ASTContext.h" | 
| Daniel Dunbar | c4a1dea | 2008-08-11 05:35:13 +0000 | [diff] [blame] | 18 | #include "clang/AST/DeclObjC.h" | 
| Daniel Dunbar | e91593e | 2008-08-11 04:54:23 +0000 | [diff] [blame] | 19 | #include "clang/AST/Expr.h" | 
| Reid Spencer | 5f016e2 | 2007-07-11 17:01:13 +0000 | [diff] [blame] | 20 | #include "clang/Lex/Preprocessor.h" | 
| Reid Spencer | 5f016e2 | 2007-07-11 17:01:13 +0000 | [diff] [blame] | 21 | using namespace clang; | 
 | 22 |  | 
| Chris Lattner | 22caddc | 2008-11-23 09:13:29 +0000 | [diff] [blame] | 23 | /// ConvertQualTypeToStringFn - This function is used to pretty print the  | 
 | 24 | /// specified QualType as a string in diagnostics. | 
| Chris Lattner | 011bb4e | 2008-11-23 20:28:15 +0000 | [diff] [blame] | 25 | static void ConvertArgToStringFn(Diagnostic::ArgumentKind Kind, intptr_t Val, | 
| Chris Lattner | d0344a4 | 2009-02-19 23:45:49 +0000 | [diff] [blame] | 26 |                                  const char *Modifier, unsigned ModLen, | 
 | 27 |                                  const char *Argument, unsigned ArgLen, | 
| Chris Lattner | 92dd386 | 2009-02-19 23:53:20 +0000 | [diff] [blame] | 28 |                                  llvm::SmallVectorImpl<char> &Output, | 
 | 29 |                                  void *Cookie) { | 
 | 30 |   ASTContext &Context = *static_cast<ASTContext*>(Cookie); | 
| Chris Lattner | 3fdf4b0 | 2008-11-23 09:21:17 +0000 | [diff] [blame] | 31 |    | 
| Chris Lattner | 011bb4e | 2008-11-23 20:28:15 +0000 | [diff] [blame] | 32 |   std::string S; | 
 | 33 |   if (Kind == Diagnostic::ak_qualtype) { | 
| Chris Lattner | d0344a4 | 2009-02-19 23:45:49 +0000 | [diff] [blame] | 34 |     assert(ModLen == 0 && ArgLen == 0 && | 
 | 35 |            "Invalid modifier for QualType argument"); | 
 | 36 |  | 
| Chris Lattner | 011bb4e | 2008-11-23 20:28:15 +0000 | [diff] [blame] | 37 |     QualType Ty(QualType::getFromOpaquePtr(reinterpret_cast<void*>(Val))); | 
| Chris Lattner | 077bf5e | 2008-11-24 03:33:13 +0000 | [diff] [blame] | 38 |  | 
| Chris Lattner | 011bb4e | 2008-11-23 20:28:15 +0000 | [diff] [blame] | 39 |     // FIXME: Playing with std::string is really slow. | 
 | 40 |     S = Ty.getAsString(); | 
| Chris Lattner | d0344a4 | 2009-02-19 23:45:49 +0000 | [diff] [blame] | 41 |      | 
 | 42 |     // If this is a sugared type (like a typedef, typeof, etc), then unwrap one | 
 | 43 |     // level of the sugar so that the type is more obvious to the user. | 
| Douglas Gregor | 969c689 | 2009-04-01 15:47:24 +0000 | [diff] [blame] | 44 |     QualType DesugaredTy = Ty->getDesugaredType(true); | 
| Chris Lattner | d0344a4 | 2009-02-19 23:45:49 +0000 | [diff] [blame] | 45 |     DesugaredTy.setCVRQualifiers(DesugaredTy.getCVRQualifiers() | | 
 | 46 |                                  Ty.getCVRQualifiers()); | 
| Chris Lattner | 077bf5e | 2008-11-24 03:33:13 +0000 | [diff] [blame] | 47 |  | 
| Chris Lattner | d0344a4 | 2009-02-19 23:45:49 +0000 | [diff] [blame] | 48 |     if (Ty != DesugaredTy && | 
 | 49 |         // If the desugared type is a vector type, we don't want to expand it, | 
 | 50 |         // it will turn into an attribute mess. People want their "vec4". | 
 | 51 |         !isa<VectorType>(DesugaredTy) && | 
 | 52 |        | 
| Chris Lattner | 92dd386 | 2009-02-19 23:53:20 +0000 | [diff] [blame] | 53 |         // Don't desugar magic Objective-C types. | 
 | 54 |         Ty.getUnqualifiedType() != Context.getObjCIdType() && | 
 | 55 |         Ty.getUnqualifiedType() != Context.getObjCSelType() && | 
 | 56 |         Ty.getUnqualifiedType() != Context.getObjCProtoType() && | 
 | 57 |         Ty.getUnqualifiedType() != Context.getObjCClassType() && | 
 | 58 |          | 
 | 59 |         // Not va_list. | 
 | 60 |         Ty.getUnqualifiedType() != Context.getBuiltinVaListType()) { | 
| Chris Lattner | d0344a4 | 2009-02-19 23:45:49 +0000 | [diff] [blame] | 61 |       S = "'"+S+"' (aka '"; | 
 | 62 |       S += DesugaredTy.getAsString(); | 
 | 63 |       S += "')"; | 
 | 64 |       Output.append(S.begin(), S.end()); | 
 | 65 |       return; | 
 | 66 |     } | 
| Chris Lattner | 077bf5e | 2008-11-24 03:33:13 +0000 | [diff] [blame] | 67 |      | 
| Douglas Gregor | 47b9a1c | 2009-02-04 17:27:36 +0000 | [diff] [blame] | 68 |   } else if (Kind == Diagnostic::ak_declarationname) { | 
| Chris Lattner | 011bb4e | 2008-11-23 20:28:15 +0000 | [diff] [blame] | 69 |     | 
 | 70 |     DeclarationName N = DeclarationName::getFromOpaqueInteger(Val); | 
 | 71 |     S = N.getAsString(); | 
| Chris Lattner | 077bf5e | 2008-11-24 03:33:13 +0000 | [diff] [blame] | 72 |      | 
 | 73 |     if (ModLen == 9 && !memcmp(Modifier, "objcclass", 9) && ArgLen == 0) | 
 | 74 |       S = '+' + S; | 
 | 75 |     else if (ModLen == 12 && !memcmp(Modifier, "objcinstance", 12) && ArgLen==0) | 
 | 76 |       S = '-' + S; | 
 | 77 |     else | 
 | 78 |       assert(ModLen == 0 && ArgLen == 0 && | 
 | 79 |              "Invalid modifier for DeclarationName argument"); | 
| Douglas Gregor | 47b9a1c | 2009-02-04 17:27:36 +0000 | [diff] [blame] | 80 |   } else { | 
 | 81 |     assert(Kind == Diagnostic::ak_nameddecl); | 
| Douglas Gregor | eeb15d4 | 2009-02-04 22:46:25 +0000 | [diff] [blame] | 82 |     if (ModLen == 1 && Modifier[0] == 'q' && ArgLen == 0) | 
 | 83 |       S = reinterpret_cast<NamedDecl*>(Val)->getQualifiedNameAsString(); | 
 | 84 |     else {  | 
 | 85 |       assert(ModLen == 0 && ArgLen == 0 && | 
| Douglas Gregor | 47b9a1c | 2009-02-04 17:27:36 +0000 | [diff] [blame] | 86 |            "Invalid modifier for NamedDecl* argument"); | 
| Douglas Gregor | eeb15d4 | 2009-02-04 22:46:25 +0000 | [diff] [blame] | 87 |       S = reinterpret_cast<NamedDecl*>(Val)->getNameAsString(); | 
 | 88 |     } | 
| Chris Lattner | 011bb4e | 2008-11-23 20:28:15 +0000 | [diff] [blame] | 89 |   } | 
| Chris Lattner | d0344a4 | 2009-02-19 23:45:49 +0000 | [diff] [blame] | 90 |    | 
 | 91 |   Output.push_back('\''); | 
| Chris Lattner | 22caddc | 2008-11-23 09:13:29 +0000 | [diff] [blame] | 92 |   Output.append(S.begin(), S.end()); | 
| Chris Lattner | d0344a4 | 2009-02-19 23:45:49 +0000 | [diff] [blame] | 93 |   Output.push_back('\''); | 
| Chris Lattner | 22caddc | 2008-11-23 09:13:29 +0000 | [diff] [blame] | 94 | } | 
 | 95 |  | 
 | 96 |  | 
| Chris Lattner | 0a14eee | 2008-11-18 07:04:44 +0000 | [diff] [blame] | 97 | static inline RecordDecl *CreateStructDecl(ASTContext &C, const char *Name) { | 
| Anders Carlsson | c303606 | 2008-08-23 22:20:38 +0000 | [diff] [blame] | 98 |   if (C.getLangOptions().CPlusPlus) | 
 | 99 |     return CXXRecordDecl::Create(C, TagDecl::TK_struct,  | 
 | 100 |                                  C.getTranslationUnitDecl(), | 
| Ted Kremenek | df042e6 | 2008-09-05 01:34:33 +0000 | [diff] [blame] | 101 |                                  SourceLocation(), &C.Idents.get(Name)); | 
| Chris Lattner | fa25bbb | 2008-11-19 05:08:23 +0000 | [diff] [blame] | 102 |  | 
 | 103 |   return RecordDecl::Create(C, TagDecl::TK_struct,  | 
 | 104 |                             C.getTranslationUnitDecl(), | 
 | 105 |                             SourceLocation(), &C.Idents.get(Name)); | 
| Anders Carlsson | c303606 | 2008-08-23 22:20:38 +0000 | [diff] [blame] | 106 | } | 
 | 107 |  | 
| Steve Naroff | b216c88 | 2007-10-09 22:01:59 +0000 | [diff] [blame] | 108 | void Sema::ActOnTranslationUnitScope(SourceLocation Loc, Scope *S) { | 
 | 109 |   TUScope = S; | 
| Douglas Gregor | 44b4321 | 2008-12-11 16:49:14 +0000 | [diff] [blame] | 110 |   PushDeclContext(S, Context.getTranslationUnitDecl()); | 
| Chris Lattner | 2ae34ed | 2008-02-06 00:46:58 +0000 | [diff] [blame] | 111 |   if (!PP.getLangOptions().ObjC1) return; | 
 | 112 |    | 
| Douglas Gregor | 319ac89 | 2009-04-23 22:29:11 +0000 | [diff] [blame] | 113 |   if (Context.getObjCSelType().isNull()) { | 
 | 114 |     // Synthesize "typedef struct objc_selector *SEL;" | 
 | 115 |     RecordDecl *SelTag = CreateStructDecl(Context, "objc_selector"); | 
 | 116 |     PushOnScopeChains(SelTag, TUScope); | 
| Steve Naroff | 69d6375 | 2008-02-24 16:25:02 +0000 | [diff] [blame] | 117 |    | 
| Douglas Gregor | 319ac89 | 2009-04-23 22:29:11 +0000 | [diff] [blame] | 118 |     QualType SelT = Context.getPointerType(Context.getTagDeclType(SelTag)); | 
 | 119 |     TypedefDecl *SelTypedef = TypedefDecl::Create(Context, CurContext, | 
 | 120 |                                                   SourceLocation(), | 
 | 121 |                                                   &Context.Idents.get("SEL"), | 
 | 122 |                                                   SelT); | 
 | 123 |     PushOnScopeChains(SelTypedef, TUScope); | 
 | 124 |     Context.setObjCSelType(Context.getTypeDeclType(SelTypedef)); | 
 | 125 |   } | 
| Chris Lattner | 6ee1f9c | 2008-06-21 20:20:39 +0000 | [diff] [blame] | 126 |  | 
| Douglas Gregor | 319ac89 | 2009-04-23 22:29:11 +0000 | [diff] [blame] | 127 |   if (Context.getObjCClassType().isNull()) { | 
 | 128 |     RecordDecl *ClassTag = CreateStructDecl(Context, "objc_class"); | 
 | 129 |     QualType ClassT = Context.getPointerType(Context.getTagDeclType(ClassTag)); | 
 | 130 |     TypedefDecl *ClassTypedef =  | 
 | 131 |       TypedefDecl::Create(Context, CurContext, SourceLocation(), | 
 | 132 |                           &Context.Idents.get("Class"), ClassT); | 
 | 133 |     PushOnScopeChains(ClassTag, TUScope); | 
 | 134 |     PushOnScopeChains(ClassTypedef, TUScope); | 
 | 135 |     Context.setObjCClassType(Context.getTypeDeclType(ClassTypedef)); | 
 | 136 |   } | 
 | 137 |  | 
| Chris Lattner | 6ee1f9c | 2008-06-21 20:20:39 +0000 | [diff] [blame] | 138 |   // Synthesize "@class Protocol; | 
| Douglas Gregor | 319ac89 | 2009-04-23 22:29:11 +0000 | [diff] [blame] | 139 |   if (Context.getObjCProtoType().isNull()) { | 
 | 140 |     ObjCInterfaceDecl *ProtocolDecl = | 
 | 141 |       ObjCInterfaceDecl::Create(Context, CurContext, SourceLocation(), | 
 | 142 |                                 &Context.Idents.get("Protocol"),  | 
 | 143 |                                 SourceLocation(), true); | 
 | 144 |     Context.setObjCProtoType(Context.getObjCInterfaceType(ProtocolDecl)); | 
 | 145 |     PushOnScopeChains(ProtocolDecl, TUScope); | 
 | 146 |   } | 
| Anders Carlsson | c303606 | 2008-08-23 22:20:38 +0000 | [diff] [blame] | 147 |  | 
| Douglas Gregor | 319ac89 | 2009-04-23 22:29:11 +0000 | [diff] [blame] | 148 |   // Synthesize "typedef struct objc_object { Class isa; } *id;" | 
 | 149 |   if (Context.getObjCIdType().isNull()) { | 
 | 150 |     RecordDecl *ObjectTag = CreateStructDecl(Context, "objc_object"); | 
 | 151 |      | 
 | 152 |     QualType ObjT = Context.getPointerType(Context.getTagDeclType(ObjectTag)); | 
 | 153 |     PushOnScopeChains(ObjectTag, TUScope); | 
 | 154 |     TypedefDecl *IdTypedef = TypedefDecl::Create(Context, CurContext, | 
 | 155 |                                                  SourceLocation(), | 
 | 156 |                                                  &Context.Idents.get("id"), | 
 | 157 |                                                  ObjT); | 
 | 158 |     PushOnScopeChains(IdTypedef, TUScope); | 
 | 159 |     Context.setObjCIdType(Context.getTypeDeclType(IdTypedef)); | 
 | 160 |   } | 
| Steve Naroff | 3b95017 | 2007-10-10 21:53:07 +0000 | [diff] [blame] | 161 | } | 
 | 162 |  | 
| Douglas Gregor | f807fe0 | 2009-04-14 16:27:31 +0000 | [diff] [blame] | 163 | Sema::Sema(Preprocessor &pp, ASTContext &ctxt, ASTConsumer &consumer, | 
 | 164 |            bool CompleteTranslationUnit) | 
| Chris Lattner | 53ebff3 | 2009-01-22 19:21:44 +0000 | [diff] [blame] | 165 |   : LangOpts(pp.getLangOptions()), PP(pp), Context(ctxt), Consumer(consumer), | 
 | 166 |     Diags(PP.getDiagnostics()), | 
| Chris Lattner | 3cfa928 | 2008-11-22 08:28:49 +0000 | [diff] [blame] | 167 |     SourceMgr(PP.getSourceManager()), CurContext(0), PreDeclaratorDC(0), | 
| Sebastian Redl | b5a57a6 | 2008-12-03 20:26:15 +0000 | [diff] [blame] | 168 |     CurBlock(0), PackContext(0), IdResolver(pp.getLangOptions()), | 
| Douglas Gregor | f807fe0 | 2009-04-14 16:27:31 +0000 | [diff] [blame] | 169 |     GlobalNewDeleteDeclared(false),  | 
 | 170 |     CompleteTranslationUnit(CompleteTranslationUnit) { | 
| Chris Lattner | 59907c4 | 2007-08-10 20:18:51 +0000 | [diff] [blame] | 171 |    | 
| Sebastian Redl | c42e118 | 2008-11-11 11:37:55 +0000 | [diff] [blame] | 172 |   StdNamespace = 0; | 
| Steve Naroff | 3b95017 | 2007-10-10 21:53:07 +0000 | [diff] [blame] | 173 |   TUScope = 0; | 
| Argyrios Kyrtzidis | 0795232 | 2008-07-01 10:37:29 +0000 | [diff] [blame] | 174 |   if (getLangOptions().CPlusPlus) | 
 | 175 |     FieldCollector.reset(new CXXFieldCollector()); | 
| Chris Lattner | 22caddc | 2008-11-23 09:13:29 +0000 | [diff] [blame] | 176 |        | 
 | 177 |   // Tell diagnostics how to render things from the AST library. | 
| Chris Lattner | 92dd386 | 2009-02-19 23:53:20 +0000 | [diff] [blame] | 178 |   PP.getDiagnostics().SetArgToStringFn(ConvertArgToStringFn, &Context); | 
| Reid Spencer | 5f016e2 | 2007-07-11 17:01:13 +0000 | [diff] [blame] | 179 | } | 
 | 180 |  | 
| Chris Lattner | 1e0a390 | 2008-01-16 19:17:22 +0000 | [diff] [blame] | 181 | /// ImpCastExprToType - If Expr is not of type 'Type', insert an implicit cast.  | 
 | 182 | /// If there is already an implicit cast, merge into the existing one. | 
| Nate Begeman | 6fe7c8a | 2009-01-18 06:42:49 +0000 | [diff] [blame] | 183 | /// If isLvalue, the result of the cast is an lvalue. | 
| Douglas Gregor | eb8f306 | 2008-11-12 17:17:38 +0000 | [diff] [blame] | 184 | void Sema::ImpCastExprToType(Expr *&Expr, QualType Ty, bool isLvalue) { | 
| Mon P Wang | 3a2c744 | 2008-09-04 08:38:01 +0000 | [diff] [blame] | 185 |   QualType ExprTy = Context.getCanonicalType(Expr->getType()); | 
 | 186 |   QualType TypeTy = Context.getCanonicalType(Ty); | 
 | 187 |    | 
 | 188 |   if (ExprTy == TypeTy) | 
 | 189 |     return; | 
 | 190 |    | 
 | 191 |   if (Expr->getType().getTypePtr()->isPointerType() && | 
 | 192 |       Ty.getTypePtr()->isPointerType()) { | 
 | 193 |     QualType ExprBaseType =  | 
 | 194 |       cast<PointerType>(ExprTy.getUnqualifiedType())->getPointeeType(); | 
 | 195 |     QualType BaseType = | 
 | 196 |       cast<PointerType>(TypeTy.getUnqualifiedType())->getPointeeType(); | 
 | 197 |     if (ExprBaseType.getAddressSpace() != BaseType.getAddressSpace()) { | 
| Chris Lattner | dcd5ef1 | 2008-11-19 05:27:50 +0000 | [diff] [blame] | 198 |       Diag(Expr->getExprLoc(), diag::err_implicit_pointer_address_space_cast) | 
 | 199 |         << Expr->getSourceRange(); | 
| Mon P Wang | 3a2c744 | 2008-09-04 08:38:01 +0000 | [diff] [blame] | 200 |     } | 
 | 201 |   } | 
| Chris Lattner | 1e0a390 | 2008-01-16 19:17:22 +0000 | [diff] [blame] | 202 |    | 
| Douglas Gregor | eb8f306 | 2008-11-12 17:17:38 +0000 | [diff] [blame] | 203 |   if (ImplicitCastExpr *ImpCast = dyn_cast<ImplicitCastExpr>(Expr)) { | 
| Mon P Wang | 3a2c744 | 2008-09-04 08:38:01 +0000 | [diff] [blame] | 204 |     ImpCast->setType(Ty); | 
| Douglas Gregor | eb8f306 | 2008-11-12 17:17:38 +0000 | [diff] [blame] | 205 |     ImpCast->setLvalueCast(isLvalue); | 
 | 206 |   } else  | 
| Ted Kremenek | 8189cde | 2009-02-07 01:47:29 +0000 | [diff] [blame] | 207 |     Expr = new (Context) ImplicitCastExpr(Ty, Expr, isLvalue); | 
| Chris Lattner | 1e0a390 | 2008-01-16 19:17:22 +0000 | [diff] [blame] | 208 | } | 
 | 209 |  | 
| Chris Lattner | 394a3fd | 2007-08-31 04:53:24 +0000 | [diff] [blame] | 210 | void Sema::DeleteExpr(ExprTy *E) { | 
| Douglas Gregor | 05c13a3 | 2009-01-22 00:58:24 +0000 | [diff] [blame] | 211 |   if (E) static_cast<Expr*>(E)->Destroy(Context); | 
| Chris Lattner | 394a3fd | 2007-08-31 04:53:24 +0000 | [diff] [blame] | 212 | } | 
 | 213 | void Sema::DeleteStmt(StmtTy *S) { | 
| Douglas Gregor | 05c13a3 | 2009-01-22 00:58:24 +0000 | [diff] [blame] | 214 |   if (S) static_cast<Stmt*>(S)->Destroy(Context); | 
| Chris Lattner | 394a3fd | 2007-08-31 04:53:24 +0000 | [diff] [blame] | 215 | } | 
 | 216 |  | 
| Chris Lattner | 9299f3f | 2008-08-23 03:19:52 +0000 | [diff] [blame] | 217 | /// ActOnEndOfTranslationUnit - This is called at the very end of the | 
 | 218 | /// translation unit when EOF is reached and all but the top-level scope is | 
 | 219 | /// popped. | 
 | 220 | void Sema::ActOnEndOfTranslationUnit() { | 
| Douglas Gregor | f807fe0 | 2009-04-14 16:27:31 +0000 | [diff] [blame] | 221 |   if (!CompleteTranslationUnit) | 
 | 222 |     return; | 
 | 223 |  | 
| Douglas Gregor | 275a369 | 2009-03-10 23:43:53 +0000 | [diff] [blame] | 224 |   // C99 6.9.2p2: | 
 | 225 |   //   A declaration of an identifier for an object that has file | 
 | 226 |   //   scope without an initializer, and without a storage-class | 
 | 227 |   //   specifier or with the storage-class specifier static, | 
 | 228 |   //   constitutes a tentative definition. If a translation unit | 
 | 229 |   //   contains one or more tentative definitions for an identifier, | 
 | 230 |   //   and the translation unit contains no external definition for | 
 | 231 |   //   that identifier, then the behavior is exactly as if the | 
 | 232 |   //   translation unit contains a file scope declaration of that | 
 | 233 |   //   identifier, with the composite type as of the end of the | 
 | 234 |   //   translation unit, with an initializer equal to 0. | 
| Douglas Gregor | b6c8c8b | 2009-04-21 17:11:58 +0000 | [diff] [blame] | 235 |   for (llvm::DenseMap<DeclarationName, VarDecl *>::iterator  | 
 | 236 |          D = TentativeDefinitions.begin(), | 
 | 237 |          DEnd = TentativeDefinitions.end(); | 
 | 238 |        D != DEnd; ++D) { | 
 | 239 |     VarDecl *VD = D->second; | 
| Chris Lattner | 9299f3f | 2008-08-23 03:19:52 +0000 | [diff] [blame] | 240 |  | 
| Douglas Gregor | b6c8c8b | 2009-04-21 17:11:58 +0000 | [diff] [blame] | 241 |     if (VD->isInvalidDecl() || !VD->isTentativeDefinition(Context)) | 
 | 242 |       continue; | 
 | 243 |  | 
 | 244 |     if (const IncompleteArrayType *ArrayT  | 
 | 245 |         = Context.getAsIncompleteArrayType(VD->getType())) { | 
 | 246 |       if (RequireCompleteType(VD->getLocation(),  | 
 | 247 |                               ArrayT->getElementType(), | 
 | 248 |                               diag::err_tentative_def_incomplete_type_arr)) | 
 | 249 |         VD->setInvalidDecl(); | 
 | 250 |       else { | 
 | 251 |         // Set the length of the array to 1 (C99 6.9.2p5). | 
 | 252 |         Diag(VD->getLocation(),  diag::warn_tentative_incomplete_array); | 
 | 253 |         llvm::APInt One(Context.getTypeSize(Context.getSizeType()),  | 
 | 254 |                         true); | 
 | 255 |         QualType T  | 
 | 256 |           = Context.getConstantArrayType(ArrayT->getElementType(), | 
 | 257 |                                          One, ArrayType::Normal, 0); | 
 | 258 |         VD->setType(T); | 
| Douglas Gregor | 275a369 | 2009-03-10 23:43:53 +0000 | [diff] [blame] | 259 |       } | 
| Douglas Gregor | b6c8c8b | 2009-04-21 17:11:58 +0000 | [diff] [blame] | 260 |     } else if (RequireCompleteType(VD->getLocation(), VD->getType(),  | 
 | 261 |                                    diag::err_tentative_def_incomplete_type)) | 
 | 262 |       VD->setInvalidDecl(); | 
 | 263 |  | 
 | 264 |     // Notify the consumer that we've completed a tentative definition. | 
 | 265 |     if (!VD->isInvalidDecl()) | 
 | 266 |       Consumer.CompleteTentativeDefinition(VD); | 
 | 267 |  | 
| Douglas Gregor | 275a369 | 2009-03-10 23:43:53 +0000 | [diff] [blame] | 268 |   } | 
| Chris Lattner | 9299f3f | 2008-08-23 03:19:52 +0000 | [diff] [blame] | 269 | } | 
 | 270 |  | 
 | 271 |  | 
| Reid Spencer | 5f016e2 | 2007-07-11 17:01:13 +0000 | [diff] [blame] | 272 | //===----------------------------------------------------------------------===// | 
 | 273 | // Helper functions. | 
 | 274 | //===----------------------------------------------------------------------===// | 
 | 275 |  | 
| Chris Lattner | 371f258 | 2008-12-04 23:50:19 +0000 | [diff] [blame] | 276 | /// getCurFunctionDecl - If inside of a function body, this returns a pointer | 
 | 277 | /// to the function decl for the function being parsed.  If we're currently | 
 | 278 | /// in a 'block', this returns the containing context. | 
 | 279 | FunctionDecl *Sema::getCurFunctionDecl() { | 
 | 280 |   DeclContext *DC = CurContext; | 
 | 281 |   while (isa<BlockDecl>(DC)) | 
 | 282 |     DC = DC->getParent(); | 
 | 283 |   return dyn_cast<FunctionDecl>(DC); | 
 | 284 | } | 
 | 285 |  | 
| Daniel Dunbar | c4a1dea | 2008-08-11 05:35:13 +0000 | [diff] [blame] | 286 | ObjCMethodDecl *Sema::getCurMethodDecl() { | 
| Steve Naroff | d7612e1 | 2008-11-17 16:28:52 +0000 | [diff] [blame] | 287 |   DeclContext *DC = CurContext; | 
 | 288 |   while (isa<BlockDecl>(DC)) | 
 | 289 |     DC = DC->getParent(); | 
 | 290 |   return dyn_cast<ObjCMethodDecl>(DC); | 
| Daniel Dunbar | c4a1dea | 2008-08-11 05:35:13 +0000 | [diff] [blame] | 291 | } | 
| Chris Lattner | 371f258 | 2008-12-04 23:50:19 +0000 | [diff] [blame] | 292 |  | 
 | 293 | NamedDecl *Sema::getCurFunctionOrMethodDecl() { | 
 | 294 |   DeclContext *DC = CurContext; | 
 | 295 |   while (isa<BlockDecl>(DC)) | 
 | 296 |     DC = DC->getParent(); | 
 | 297 |   if (isa<ObjCMethodDecl>(DC) || isa<FunctionDecl>(DC)) | 
| Douglas Gregor | 4afa39d | 2009-01-20 01:17:11 +0000 | [diff] [blame] | 298 |     return cast<NamedDecl>(DC); | 
| Chris Lattner | 371f258 | 2008-12-04 23:50:19 +0000 | [diff] [blame] | 299 |   return 0; | 
 | 300 | } | 
 | 301 |  | 
| Douglas Gregor | 25a88bb | 2009-03-20 22:48:49 +0000 | [diff] [blame] | 302 | Sema::SemaDiagnosticBuilder::~SemaDiagnosticBuilder() { | 
 | 303 |   this->Emit(); | 
 | 304 |    | 
 | 305 |   // If this is not a note, and we're in a template instantiation | 
 | 306 |   // that is different from the last template instantiation where | 
 | 307 |   // we emitted an error, print a template instantiation | 
 | 308 |   // backtrace. | 
 | 309 |   if (!SemaRef.Diags.isBuiltinNote(DiagID) && | 
 | 310 |       !SemaRef.ActiveTemplateInstantiations.empty() && | 
 | 311 |       SemaRef.ActiveTemplateInstantiations.back()  | 
 | 312 |         != SemaRef.LastTemplateInstantiationErrorContext) { | 
 | 313 |     SemaRef.PrintInstantiationStack(); | 
 | 314 |     SemaRef.LastTemplateInstantiationErrorContext  | 
 | 315 |       = SemaRef.ActiveTemplateInstantiations.back(); | 
 | 316 |   } | 
 | 317 | } |