1 //===--- ASTWriterDecl.cpp - Declaration Serialization --------------------===//
3 // The LLVM Compiler Infrastructure
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
8 //===----------------------------------------------------------------------===//
10 // This file implements serialization for Declarations.
12 //===----------------------------------------------------------------------===//
14 #include "clang/Serialization/ASTWriter.h"
15 #include "clang/AST/DeclVisitor.h"
16 #include "clang/AST/DeclCXX.h"
17 #include "clang/AST/DeclTemplate.h"
18 #include "clang/AST/Expr.h"
19 #include "clang/AST/DeclContextInternals.h"
20 #include "llvm/ADT/Twine.h"
21 #include "llvm/Bitcode/BitstreamWriter.h"
22 #include "llvm/Support/ErrorHandling.h"
23 using namespace clang
;
25 //===----------------------------------------------------------------------===//
26 // Declaration serialization
27 //===----------------------------------------------------------------------===//
30 class ASTDeclWriter
: public DeclVisitor
<ASTDeclWriter
, void> {
34 typedef ASTWriter::RecordData RecordData
;
38 serialization::DeclCode Code
;
41 ASTDeclWriter(ASTWriter
&Writer
, ASTContext
&Context
, RecordData
&Record
)
42 : Writer(Writer
), Context(Context
), Record(Record
) {
47 void VisitDecl(Decl
*D
);
48 void VisitTranslationUnitDecl(TranslationUnitDecl
*D
);
49 void VisitNamedDecl(NamedDecl
*D
);
50 void VisitNamespaceDecl(NamespaceDecl
*D
);
51 void VisitUsingDirectiveDecl(UsingDirectiveDecl
*D
);
52 void VisitNamespaceAliasDecl(NamespaceAliasDecl
*D
);
53 void VisitTypeDecl(TypeDecl
*D
);
54 void VisitTypedefDecl(TypedefDecl
*D
);
55 void VisitUnresolvedUsingTypenameDecl(UnresolvedUsingTypenameDecl
*D
);
56 void VisitTagDecl(TagDecl
*D
);
57 void VisitEnumDecl(EnumDecl
*D
);
58 void VisitRecordDecl(RecordDecl
*D
);
59 void VisitCXXRecordDecl(CXXRecordDecl
*D
);
60 void VisitClassTemplateSpecializationDecl(
61 ClassTemplateSpecializationDecl
*D
);
62 void VisitClassTemplatePartialSpecializationDecl(
63 ClassTemplatePartialSpecializationDecl
*D
);
64 void VisitTemplateTypeParmDecl(TemplateTypeParmDecl
*D
);
65 void VisitValueDecl(ValueDecl
*D
);
66 void VisitEnumConstantDecl(EnumConstantDecl
*D
);
67 void VisitUnresolvedUsingValueDecl(UnresolvedUsingValueDecl
*D
);
68 void VisitDeclaratorDecl(DeclaratorDecl
*D
);
69 void VisitFunctionDecl(FunctionDecl
*D
);
70 void VisitCXXMethodDecl(CXXMethodDecl
*D
);
71 void VisitCXXConstructorDecl(CXXConstructorDecl
*D
);
72 void VisitCXXDestructorDecl(CXXDestructorDecl
*D
);
73 void VisitCXXConversionDecl(CXXConversionDecl
*D
);
74 void VisitFieldDecl(FieldDecl
*D
);
75 void VisitIndirectFieldDecl(IndirectFieldDecl
*D
);
76 void VisitVarDecl(VarDecl
*D
);
77 void VisitImplicitParamDecl(ImplicitParamDecl
*D
);
78 void VisitParmVarDecl(ParmVarDecl
*D
);
79 void VisitNonTypeTemplateParmDecl(NonTypeTemplateParmDecl
*D
);
80 void VisitTemplateDecl(TemplateDecl
*D
);
81 void VisitRedeclarableTemplateDecl(RedeclarableTemplateDecl
*D
);
82 void VisitClassTemplateDecl(ClassTemplateDecl
*D
);
83 void VisitFunctionTemplateDecl(FunctionTemplateDecl
*D
);
84 void VisitTemplateTemplateParmDecl(TemplateTemplateParmDecl
*D
);
85 void VisitUsingDecl(UsingDecl
*D
);
86 void VisitUsingShadowDecl(UsingShadowDecl
*D
);
87 void VisitLinkageSpecDecl(LinkageSpecDecl
*D
);
88 void VisitFileScopeAsmDecl(FileScopeAsmDecl
*D
);
89 void VisitAccessSpecDecl(AccessSpecDecl
*D
);
90 void VisitFriendDecl(FriendDecl
*D
);
91 void VisitFriendTemplateDecl(FriendTemplateDecl
*D
);
92 void VisitStaticAssertDecl(StaticAssertDecl
*D
);
93 void VisitBlockDecl(BlockDecl
*D
);
95 void VisitDeclContext(DeclContext
*DC
, uint64_t LexicalOffset
,
96 uint64_t VisibleOffset
);
97 template <typename T
> void VisitRedeclarable(Redeclarable
<T
> *D
);
100 // FIXME: Put in the same order is DeclNodes.td?
101 void VisitObjCMethodDecl(ObjCMethodDecl
*D
);
102 void VisitObjCContainerDecl(ObjCContainerDecl
*D
);
103 void VisitObjCInterfaceDecl(ObjCInterfaceDecl
*D
);
104 void VisitObjCIvarDecl(ObjCIvarDecl
*D
);
105 void VisitObjCProtocolDecl(ObjCProtocolDecl
*D
);
106 void VisitObjCAtDefsFieldDecl(ObjCAtDefsFieldDecl
*D
);
107 void VisitObjCClassDecl(ObjCClassDecl
*D
);
108 void VisitObjCForwardProtocolDecl(ObjCForwardProtocolDecl
*D
);
109 void VisitObjCCategoryDecl(ObjCCategoryDecl
*D
);
110 void VisitObjCImplDecl(ObjCImplDecl
*D
);
111 void VisitObjCCategoryImplDecl(ObjCCategoryImplDecl
*D
);
112 void VisitObjCImplementationDecl(ObjCImplementationDecl
*D
);
113 void VisitObjCCompatibleAliasDecl(ObjCCompatibleAliasDecl
*D
);
114 void VisitObjCPropertyDecl(ObjCPropertyDecl
*D
);
115 void VisitObjCPropertyImplDecl(ObjCPropertyImplDecl
*D
);
119 void ASTDeclWriter::Visit(Decl
*D
) {
120 DeclVisitor
<ASTDeclWriter
>::Visit(D
);
122 // Handle FunctionDecl's body here and write it after all other Stmts/Exprs
123 // have been written. We want it last because we will not read it back when
124 // retrieving it from the AST, we'll just lazily set the offset.
125 if (FunctionDecl
*FD
= dyn_cast
<FunctionDecl
>(D
)) {
126 Record
.push_back(FD
->isThisDeclarationADefinition());
127 if (FD
->isThisDeclarationADefinition())
128 Writer
.AddStmt(FD
->getBody());
132 void ASTDeclWriter::VisitDecl(Decl
*D
) {
133 Writer
.AddDeclRef(cast_or_null
<Decl
>(D
->getDeclContext()), Record
);
134 Writer
.AddDeclRef(cast_or_null
<Decl
>(D
->getLexicalDeclContext()), Record
);
135 Writer
.AddSourceLocation(D
->getLocation(), Record
);
136 Record
.push_back(D
->isInvalidDecl());
137 Record
.push_back(D
->hasAttrs());
139 Writer
.WriteAttributes(D
->getAttrs(), Record
);
140 Record
.push_back(D
->isImplicit());
141 Record
.push_back(D
->isUsed(false));
142 Record
.push_back(D
->getAccess());
143 Record
.push_back(D
->getPCHLevel());
146 void ASTDeclWriter::VisitTranslationUnitDecl(TranslationUnitDecl
*D
) {
148 Writer
.AddDeclRef(D
->getAnonymousNamespace(), Record
);
149 Code
= serialization::DECL_TRANSLATION_UNIT
;
152 void ASTDeclWriter::VisitNamedDecl(NamedDecl
*D
) {
154 Writer
.AddDeclarationName(D
->getDeclName(), Record
);
157 void ASTDeclWriter::VisitTypeDecl(TypeDecl
*D
) {
159 Writer
.AddTypeRef(QualType(D
->getTypeForDecl(), 0), Record
);
162 void ASTDeclWriter::VisitTypedefDecl(TypedefDecl
*D
) {
164 Writer
.AddTypeSourceInfo(D
->getTypeSourceInfo(), Record
);
165 Code
= serialization::DECL_TYPEDEF
;
168 void ASTDeclWriter::VisitTagDecl(TagDecl
*D
) {
170 VisitRedeclarable(D
);
171 Record
.push_back(D
->getIdentifierNamespace());
172 Record
.push_back((unsigned)D
->getTagKind()); // FIXME: stable encoding
173 Record
.push_back(D
->isDefinition());
174 Record
.push_back(D
->isEmbeddedInDeclarator());
175 Writer
.AddSourceLocation(D
->getRBraceLoc(), Record
);
176 Writer
.AddSourceLocation(D
->getTagKeywordLoc(), Record
);
177 Record
.push_back(D
->hasExtInfo());
179 Writer
.AddQualifierInfo(*D
->getExtInfo(), Record
);
181 Writer
.AddDeclRef(D
->getTypedefForAnonDecl(), Record
);
184 void ASTDeclWriter::VisitEnumDecl(EnumDecl
*D
) {
186 Writer
.AddTypeSourceInfo(D
->getIntegerTypeSourceInfo(), Record
);
187 if (!D
->getIntegerTypeSourceInfo())
188 Writer
.AddTypeRef(D
->getIntegerType(), Record
);
189 Writer
.AddTypeRef(D
->getPromotionType(), Record
);
190 Record
.push_back(D
->getNumPositiveBits());
191 Record
.push_back(D
->getNumNegativeBits());
192 Record
.push_back(D
->isScoped());
193 Record
.push_back(D
->isScopedUsingClassTag());
194 Record
.push_back(D
->isFixed());
195 Writer
.AddDeclRef(D
->getInstantiatedFromMemberEnum(), Record
);
196 Code
= serialization::DECL_ENUM
;
199 void ASTDeclWriter::VisitRecordDecl(RecordDecl
*D
) {
201 Record
.push_back(D
->hasFlexibleArrayMember());
202 Record
.push_back(D
->isAnonymousStructOrUnion());
203 Record
.push_back(D
->hasObjectMember());
204 Code
= serialization::DECL_RECORD
;
207 void ASTDeclWriter::VisitValueDecl(ValueDecl
*D
) {
209 Writer
.AddTypeRef(D
->getType(), Record
);
212 void ASTDeclWriter::VisitEnumConstantDecl(EnumConstantDecl
*D
) {
214 Record
.push_back(D
->getInitExpr()? 1 : 0);
215 if (D
->getInitExpr())
216 Writer
.AddStmt(D
->getInitExpr());
217 Writer
.AddAPSInt(D
->getInitVal(), Record
);
218 Code
= serialization::DECL_ENUM_CONSTANT
;
221 void ASTDeclWriter::VisitDeclaratorDecl(DeclaratorDecl
*D
) {
223 Record
.push_back(D
->hasExtInfo());
225 Writer
.AddQualifierInfo(*D
->getExtInfo(), Record
);
226 Writer
.AddTypeSourceInfo(D
->getTypeSourceInfo(), Record
);
229 void ASTDeclWriter::VisitFunctionDecl(FunctionDecl
*D
) {
230 VisitDeclaratorDecl(D
);
231 VisitRedeclarable(D
);
233 Writer
.AddDeclarationNameLoc(D
->DNLoc
, D
->getDeclName(), Record
);
234 Record
.push_back(D
->getIdentifierNamespace());
235 Record
.push_back(D
->getTemplatedKind());
236 switch (D
->getTemplatedKind()) {
237 default: assert(false && "Unhandled TemplatedKind!");
239 case FunctionDecl::TK_NonTemplate
:
241 case FunctionDecl::TK_FunctionTemplate
:
242 Writer
.AddDeclRef(D
->getDescribedFunctionTemplate(), Record
);
244 case FunctionDecl::TK_MemberSpecialization
: {
245 MemberSpecializationInfo
*MemberInfo
= D
->getMemberSpecializationInfo();
246 Writer
.AddDeclRef(MemberInfo
->getInstantiatedFrom(), Record
);
247 Record
.push_back(MemberInfo
->getTemplateSpecializationKind());
248 Writer
.AddSourceLocation(MemberInfo
->getPointOfInstantiation(), Record
);
251 case FunctionDecl::TK_FunctionTemplateSpecialization
: {
252 FunctionTemplateSpecializationInfo
*
253 FTSInfo
= D
->getTemplateSpecializationInfo();
254 Writer
.AddDeclRef(FTSInfo
->getTemplate(), Record
);
255 Record
.push_back(FTSInfo
->getTemplateSpecializationKind());
257 // Template arguments.
258 Writer
.AddTemplateArgumentList(FTSInfo
->TemplateArguments
, Record
);
260 // Template args as written.
261 Record
.push_back(FTSInfo
->TemplateArgumentsAsWritten
!= 0);
262 if (FTSInfo
->TemplateArgumentsAsWritten
) {
263 Record
.push_back(FTSInfo
->TemplateArgumentsAsWritten
->size());
264 for (int i
=0, e
= FTSInfo
->TemplateArgumentsAsWritten
->size(); i
!=e
; ++i
)
265 Writer
.AddTemplateArgumentLoc((*FTSInfo
->TemplateArgumentsAsWritten
)[i
],
267 Writer
.AddSourceLocation(FTSInfo
->TemplateArgumentsAsWritten
->getLAngleLoc(),
269 Writer
.AddSourceLocation(FTSInfo
->TemplateArgumentsAsWritten
->getRAngleLoc(),
273 Writer
.AddSourceLocation(FTSInfo
->getPointOfInstantiation(), Record
);
275 if (D
->isCanonicalDecl()) {
276 // Write the template that contains the specializations set. We will
277 // add a FunctionTemplateSpecializationInfo to it when reading.
278 Writer
.AddDeclRef(FTSInfo
->getTemplate()->getCanonicalDecl(), Record
);
282 case FunctionDecl::TK_DependentFunctionTemplateSpecialization
: {
283 DependentFunctionTemplateSpecializationInfo
*
284 DFTSInfo
= D
->getDependentSpecializationInfo();
287 Record
.push_back(DFTSInfo
->getNumTemplates());
288 for (int i
=0, e
= DFTSInfo
->getNumTemplates(); i
!= e
; ++i
)
289 Writer
.AddDeclRef(DFTSInfo
->getTemplate(i
), Record
);
292 Record
.push_back(DFTSInfo
->getNumTemplateArgs());
293 for (int i
=0, e
= DFTSInfo
->getNumTemplateArgs(); i
!= e
; ++i
)
294 Writer
.AddTemplateArgumentLoc(DFTSInfo
->getTemplateArg(i
), Record
);
295 Writer
.AddSourceLocation(DFTSInfo
->getLAngleLoc(), Record
);
296 Writer
.AddSourceLocation(DFTSInfo
->getRAngleLoc(), Record
);
301 // FunctionDecl's body is handled last at ASTWriterDecl::Visit,
302 // after everything else is written.
304 Record
.push_back(D
->getStorageClass()); // FIXME: stable encoding
305 Record
.push_back(D
->getStorageClassAsWritten());
306 Record
.push_back(D
->IsInline
);
307 Record
.push_back(D
->isInlineSpecified());
308 Record
.push_back(D
->isVirtualAsWritten());
309 Record
.push_back(D
->isPure());
310 Record
.push_back(D
->hasInheritedPrototype());
311 Record
.push_back(D
->hasWrittenPrototype());
312 Record
.push_back(D
->isDeleted());
313 Record
.push_back(D
->isTrivial());
314 Record
.push_back(D
->hasImplicitReturnZero());
315 Writer
.AddSourceLocation(D
->getLocEnd(), Record
);
317 Record
.push_back(D
->param_size());
318 for (FunctionDecl::param_iterator P
= D
->param_begin(), PEnd
= D
->param_end();
320 Writer
.AddDeclRef(*P
, Record
);
321 Code
= serialization::DECL_FUNCTION
;
324 void ASTDeclWriter::VisitObjCMethodDecl(ObjCMethodDecl
*D
) {
326 // FIXME: convert to LazyStmtPtr?
327 // Unlike C/C++, method bodies will never be in header files.
328 bool HasBodyStuff
= D
->getBody() != 0 ||
329 D
->getSelfDecl() != 0 || D
->getCmdDecl() != 0;
330 Record
.push_back(HasBodyStuff
);
332 Writer
.AddStmt(D
->getBody());
333 Writer
.AddDeclRef(D
->getSelfDecl(), Record
);
334 Writer
.AddDeclRef(D
->getCmdDecl(), Record
);
336 Record
.push_back(D
->isInstanceMethod());
337 Record
.push_back(D
->isVariadic());
338 Record
.push_back(D
->isSynthesized());
339 Record
.push_back(D
->isDefined());
340 // FIXME: stable encoding for @required/@optional
341 Record
.push_back(D
->getImplementationControl());
342 // FIXME: stable encoding for in/out/inout/bycopy/byref/oneway
343 Record
.push_back(D
->getObjCDeclQualifier());
344 Record
.push_back(D
->getNumSelectorArgs());
345 Writer
.AddTypeRef(D
->getResultType(), Record
);
346 Writer
.AddTypeSourceInfo(D
->getResultTypeSourceInfo(), Record
);
347 Writer
.AddSourceLocation(D
->getLocEnd(), Record
);
348 Record
.push_back(D
->param_size());
349 for (ObjCMethodDecl::param_iterator P
= D
->param_begin(),
350 PEnd
= D
->param_end(); P
!= PEnd
; ++P
)
351 Writer
.AddDeclRef(*P
, Record
);
352 Code
= serialization::DECL_OBJC_METHOD
;
355 void ASTDeclWriter::VisitObjCContainerDecl(ObjCContainerDecl
*D
) {
357 Writer
.AddSourceRange(D
->getAtEndRange(), Record
);
358 // Abstract class (no need to define a stable serialization::DECL code).
361 void ASTDeclWriter::VisitObjCInterfaceDecl(ObjCInterfaceDecl
*D
) {
362 VisitObjCContainerDecl(D
);
363 Writer
.AddTypeRef(QualType(D
->getTypeForDecl(), 0), Record
);
364 Writer
.AddDeclRef(D
->getSuperClass(), Record
);
366 // Write out the protocols that are directly referenced by the @interface.
367 Record
.push_back(D
->ReferencedProtocols
.size());
368 for (ObjCInterfaceDecl::protocol_iterator P
= D
->protocol_begin(),
369 PEnd
= D
->protocol_end();
371 Writer
.AddDeclRef(*P
, Record
);
372 for (ObjCInterfaceDecl::protocol_loc_iterator PL
= D
->protocol_loc_begin(),
373 PLEnd
= D
->protocol_loc_end();
375 Writer
.AddSourceLocation(*PL
, Record
);
377 // Write out the protocols that are transitively referenced.
378 Record
.push_back(D
->AllReferencedProtocols
.size());
379 for (ObjCList
<ObjCProtocolDecl
>::iterator
380 P
= D
->AllReferencedProtocols
.begin(),
381 PEnd
= D
->AllReferencedProtocols
.end();
383 Writer
.AddDeclRef(*P
, Record
);
385 // Write out the ivars.
386 Record
.push_back(D
->ivar_size());
387 for (ObjCInterfaceDecl::ivar_iterator I
= D
->ivar_begin(),
388 IEnd
= D
->ivar_end(); I
!= IEnd
; ++I
)
389 Writer
.AddDeclRef(*I
, Record
);
390 Writer
.AddDeclRef(D
->getCategoryList(), Record
);
391 Record
.push_back(D
->isForwardDecl());
392 Record
.push_back(D
->isImplicitInterfaceDecl());
393 Writer
.AddSourceLocation(D
->getClassLoc(), Record
);
394 Writer
.AddSourceLocation(D
->getSuperClassLoc(), Record
);
395 Writer
.AddSourceLocation(D
->getLocEnd(), Record
);
396 Code
= serialization::DECL_OBJC_INTERFACE
;
399 void ASTDeclWriter::VisitObjCIvarDecl(ObjCIvarDecl
*D
) {
401 // FIXME: stable encoding for @public/@private/@protected/@package
402 Record
.push_back(D
->getAccessControl());
403 Record
.push_back(D
->getSynthesize());
404 Code
= serialization::DECL_OBJC_IVAR
;
407 void ASTDeclWriter::VisitObjCProtocolDecl(ObjCProtocolDecl
*D
) {
408 VisitObjCContainerDecl(D
);
409 Record
.push_back(D
->isForwardDecl());
410 Writer
.AddSourceLocation(D
->getLocEnd(), Record
);
411 Record
.push_back(D
->protocol_size());
412 for (ObjCProtocolDecl::protocol_iterator
413 I
= D
->protocol_begin(), IEnd
= D
->protocol_end(); I
!= IEnd
; ++I
)
414 Writer
.AddDeclRef(*I
, Record
);
415 for (ObjCProtocolDecl::protocol_loc_iterator PL
= D
->protocol_loc_begin(),
416 PLEnd
= D
->protocol_loc_end();
418 Writer
.AddSourceLocation(*PL
, Record
);
419 Code
= serialization::DECL_OBJC_PROTOCOL
;
422 void ASTDeclWriter::VisitObjCAtDefsFieldDecl(ObjCAtDefsFieldDecl
*D
) {
424 Code
= serialization::DECL_OBJC_AT_DEFS_FIELD
;
427 void ASTDeclWriter::VisitObjCClassDecl(ObjCClassDecl
*D
) {
429 Record
.push_back(D
->size());
430 for (ObjCClassDecl::iterator I
= D
->begin(), IEnd
= D
->end(); I
!= IEnd
; ++I
)
431 Writer
.AddDeclRef(I
->getInterface(), Record
);
432 for (ObjCClassDecl::iterator I
= D
->begin(), IEnd
= D
->end(); I
!= IEnd
; ++I
)
433 Writer
.AddSourceLocation(I
->getLocation(), Record
);
434 Code
= serialization::DECL_OBJC_CLASS
;
437 void ASTDeclWriter::VisitObjCForwardProtocolDecl(ObjCForwardProtocolDecl
*D
) {
439 Record
.push_back(D
->protocol_size());
440 for (ObjCForwardProtocolDecl::protocol_iterator
441 I
= D
->protocol_begin(), IEnd
= D
->protocol_end(); I
!= IEnd
; ++I
)
442 Writer
.AddDeclRef(*I
, Record
);
443 for (ObjCForwardProtocolDecl::protocol_loc_iterator
444 PL
= D
->protocol_loc_begin(), PLEnd
= D
->protocol_loc_end();
446 Writer
.AddSourceLocation(*PL
, Record
);
447 Code
= serialization::DECL_OBJC_FORWARD_PROTOCOL
;
450 void ASTDeclWriter::VisitObjCCategoryDecl(ObjCCategoryDecl
*D
) {
451 VisitObjCContainerDecl(D
);
452 Writer
.AddDeclRef(D
->getClassInterface(), Record
);
453 Record
.push_back(D
->protocol_size());
454 for (ObjCCategoryDecl::protocol_iterator
455 I
= D
->protocol_begin(), IEnd
= D
->protocol_end(); I
!= IEnd
; ++I
)
456 Writer
.AddDeclRef(*I
, Record
);
457 for (ObjCCategoryDecl::protocol_loc_iterator
458 PL
= D
->protocol_loc_begin(), PLEnd
= D
->protocol_loc_end();
460 Writer
.AddSourceLocation(*PL
, Record
);
461 Writer
.AddDeclRef(D
->getNextClassCategory(), Record
);
462 Record
.push_back(D
->hasSynthBitfield());
463 Writer
.AddSourceLocation(D
->getAtLoc(), Record
);
464 Writer
.AddSourceLocation(D
->getCategoryNameLoc(), Record
);
465 Code
= serialization::DECL_OBJC_CATEGORY
;
468 void ASTDeclWriter::VisitObjCCompatibleAliasDecl(ObjCCompatibleAliasDecl
*D
) {
470 Writer
.AddDeclRef(D
->getClassInterface(), Record
);
471 Code
= serialization::DECL_OBJC_COMPATIBLE_ALIAS
;
474 void ASTDeclWriter::VisitObjCPropertyDecl(ObjCPropertyDecl
*D
) {
476 Writer
.AddSourceLocation(D
->getAtLoc(), Record
);
477 Writer
.AddTypeSourceInfo(D
->getTypeSourceInfo(), Record
);
478 // FIXME: stable encoding
479 Record
.push_back((unsigned)D
->getPropertyAttributes());
480 Record
.push_back((unsigned)D
->getPropertyAttributesAsWritten());
481 // FIXME: stable encoding
482 Record
.push_back((unsigned)D
->getPropertyImplementation());
483 Writer
.AddDeclarationName(D
->getGetterName(), Record
);
484 Writer
.AddDeclarationName(D
->getSetterName(), Record
);
485 Writer
.AddDeclRef(D
->getGetterMethodDecl(), Record
);
486 Writer
.AddDeclRef(D
->getSetterMethodDecl(), Record
);
487 Writer
.AddDeclRef(D
->getPropertyIvarDecl(), Record
);
488 Code
= serialization::DECL_OBJC_PROPERTY
;
491 void ASTDeclWriter::VisitObjCImplDecl(ObjCImplDecl
*D
) {
492 VisitObjCContainerDecl(D
);
493 Writer
.AddDeclRef(D
->getClassInterface(), Record
);
494 // Abstract class (no need to define a stable serialization::DECL code).
497 void ASTDeclWriter::VisitObjCCategoryImplDecl(ObjCCategoryImplDecl
*D
) {
498 VisitObjCImplDecl(D
);
499 Writer
.AddIdentifierRef(D
->getIdentifier(), Record
);
500 Code
= serialization::DECL_OBJC_CATEGORY_IMPL
;
503 void ASTDeclWriter::VisitObjCImplementationDecl(ObjCImplementationDecl
*D
) {
504 VisitObjCImplDecl(D
);
505 Writer
.AddDeclRef(D
->getSuperClass(), Record
);
506 Writer
.AddCXXBaseOrMemberInitializers(D
->IvarInitializers
,
507 D
->NumIvarInitializers
, Record
);
508 Record
.push_back(D
->hasSynthBitfield());
509 Code
= serialization::DECL_OBJC_IMPLEMENTATION
;
512 void ASTDeclWriter::VisitObjCPropertyImplDecl(ObjCPropertyImplDecl
*D
) {
514 Writer
.AddSourceLocation(D
->getLocStart(), Record
);
515 Writer
.AddDeclRef(D
->getPropertyDecl(), Record
);
516 Writer
.AddDeclRef(D
->getPropertyIvarDecl(), Record
);
517 Writer
.AddSourceLocation(D
->getPropertyIvarDeclLoc(), Record
);
518 Writer
.AddStmt(D
->getGetterCXXConstructor());
519 Writer
.AddStmt(D
->getSetterCXXAssignment());
520 Code
= serialization::DECL_OBJC_PROPERTY_IMPL
;
523 void ASTDeclWriter::VisitFieldDecl(FieldDecl
*D
) {
524 VisitDeclaratorDecl(D
);
525 Record
.push_back(D
->isMutable());
526 Record
.push_back(D
->getBitWidth()? 1 : 0);
527 if (D
->getBitWidth())
528 Writer
.AddStmt(D
->getBitWidth());
529 if (!D
->getDeclName())
530 Writer
.AddDeclRef(Context
.getInstantiatedFromUnnamedFieldDecl(D
), Record
);
531 Code
= serialization::DECL_FIELD
;
534 void ASTDeclWriter::VisitIndirectFieldDecl(IndirectFieldDecl
*D
) {
536 Record
.push_back(D
->getChainingSize());
538 for (IndirectFieldDecl::chain_iterator
539 P
= D
->chain_begin(),
540 PEnd
= D
->chain_end(); P
!= PEnd
; ++P
)
541 Writer
.AddDeclRef(*P
, Record
);
542 Code
= serialization::DECL_INDIRECTFIELD
;
545 void ASTDeclWriter::VisitVarDecl(VarDecl
*D
) {
546 VisitDeclaratorDecl(D
);
547 VisitRedeclarable(D
);
548 Record
.push_back(D
->getStorageClass()); // FIXME: stable encoding
549 Record
.push_back(D
->getStorageClassAsWritten());
550 Record
.push_back(D
->isThreadSpecified());
551 Record
.push_back(D
->hasCXXDirectInitializer());
552 Record
.push_back(D
->isExceptionVariable());
553 Record
.push_back(D
->isNRVOVariable());
554 Record
.push_back(D
->getInit() ? 1 : 0);
556 Writer
.AddStmt(D
->getInit());
558 MemberSpecializationInfo
*SpecInfo
559 = D
->isStaticDataMember() ? D
->getMemberSpecializationInfo() : 0;
560 Record
.push_back(SpecInfo
!= 0);
562 Writer
.AddDeclRef(SpecInfo
->getInstantiatedFrom(), Record
);
563 Record
.push_back(SpecInfo
->getTemplateSpecializationKind());
564 Writer
.AddSourceLocation(SpecInfo
->getPointOfInstantiation(), Record
);
567 Code
= serialization::DECL_VAR
;
570 void ASTDeclWriter::VisitImplicitParamDecl(ImplicitParamDecl
*D
) {
572 Code
= serialization::DECL_IMPLICIT_PARAM
;
575 void ASTDeclWriter::VisitParmVarDecl(ParmVarDecl
*D
) {
577 Record
.push_back(D
->getObjCDeclQualifier()); // FIXME: stable encoding
578 Record
.push_back(D
->hasInheritedDefaultArg());
579 Record
.push_back(D
->hasUninstantiatedDefaultArg());
580 if (D
->hasUninstantiatedDefaultArg())
581 Writer
.AddStmt(D
->getUninstantiatedDefaultArg());
582 Code
= serialization::DECL_PARM_VAR
;
584 // If the assumptions about the DECL_PARM_VAR abbrev are true, use it. Here
585 // we dynamically check for the properties that we optimize for, but don't
586 // know are true of all PARM_VAR_DECLs.
587 if (!D
->getTypeSourceInfo() &&
591 D
->getAccess() == AS_none
&&
592 D
->getPCHLevel() == 0 &&
593 D
->getStorageClass() == 0 &&
594 !D
->hasCXXDirectInitializer() && // Can params have this ever?
595 D
->getObjCDeclQualifier() == 0 &&
596 !D
->hasInheritedDefaultArg() &&
598 !D
->hasUninstantiatedDefaultArg()) // No default expr.
599 AbbrevToUse
= Writer
.getParmVarDeclAbbrev();
601 // Check things we know are true of *every* PARM_VAR_DECL, which is more than
602 // just us assuming it.
603 assert(!D
->isInvalidDecl() && "Shouldn't emit invalid decls");
604 assert(!D
->isThreadSpecified() && "PARM_VAR_DECL can't be __thread");
605 assert(D
->getAccess() == AS_none
&& "PARM_VAR_DECL can't be public/private");
606 assert(!D
->isExceptionVariable() && "PARM_VAR_DECL can't be exception var");
607 assert(D
->getPreviousDeclaration() == 0 && "PARM_VAR_DECL can't be redecl");
608 assert(!D
->isStaticDataMember() &&
609 "PARM_VAR_DECL can't be static data member");
612 void ASTDeclWriter::VisitFileScopeAsmDecl(FileScopeAsmDecl
*D
) {
614 Writer
.AddStmt(D
->getAsmString());
615 Code
= serialization::DECL_FILE_SCOPE_ASM
;
618 void ASTDeclWriter::VisitBlockDecl(BlockDecl
*D
) {
620 Writer
.AddStmt(D
->getBody());
621 Writer
.AddTypeSourceInfo(D
->getSignatureAsWritten(), Record
);
622 Record
.push_back(D
->param_size());
623 for (FunctionDecl::param_iterator P
= D
->param_begin(), PEnd
= D
->param_end();
625 Writer
.AddDeclRef(*P
, Record
);
626 Code
= serialization::DECL_BLOCK
;
629 void ASTDeclWriter::VisitLinkageSpecDecl(LinkageSpecDecl
*D
) {
631 // FIXME: It might be nice to serialize the brace locations for this
632 // declaration, which don't seem to be readily available in the AST.
633 Record
.push_back(D
->getLanguage());
634 Record
.push_back(D
->hasBraces());
635 Code
= serialization::DECL_LINKAGE_SPEC
;
638 void ASTDeclWriter::VisitNamespaceDecl(NamespaceDecl
*D
) {
640 Record
.push_back(D
->isInline());
641 Writer
.AddSourceLocation(D
->getLBracLoc(), Record
);
642 Writer
.AddSourceLocation(D
->getRBracLoc(), Record
);
643 Writer
.AddDeclRef(D
->getNextNamespace(), Record
);
645 // Only write one reference--original or anonymous
646 Record
.push_back(D
->isOriginalNamespace());
647 if (D
->isOriginalNamespace())
648 Writer
.AddDeclRef(D
->getAnonymousNamespace(), Record
);
650 Writer
.AddDeclRef(D
->getOriginalNamespace(), Record
);
651 Code
= serialization::DECL_NAMESPACE
;
653 if (Writer
.hasChain() && !D
->isOriginalNamespace() &&
654 D
->getOriginalNamespace()->getPCHLevel() > 0) {
655 NamespaceDecl
*NS
= D
->getOriginalNamespace();
656 Writer
.AddUpdatedDeclContext(NS
);
658 // Make sure all visible decls are written. They will be recorded later.
659 NS
->lookup(DeclarationName());
660 StoredDeclsMap
*Map
= static_cast<StoredDeclsMap
*>(NS
->getLookupPtr());
662 for (StoredDeclsMap::iterator D
= Map
->begin(), DEnd
= Map
->end();
664 DeclarationName Name
= D
->first
;
665 DeclContext::lookup_result Result
= D
->second
.getLookupResult();
666 while (Result
.first
!= Result
.second
) {
667 Writer
.GetDeclRef(*Result
.first
);
675 void ASTDeclWriter::VisitNamespaceAliasDecl(NamespaceAliasDecl
*D
) {
677 Writer
.AddSourceLocation(D
->getNamespaceLoc(), Record
);
678 Writer
.AddSourceRange(D
->getQualifierRange(), Record
);
679 Writer
.AddNestedNameSpecifier(D
->getQualifier(), Record
);
680 Writer
.AddSourceLocation(D
->getTargetNameLoc(), Record
);
681 Writer
.AddDeclRef(D
->getNamespace(), Record
);
682 Code
= serialization::DECL_NAMESPACE_ALIAS
;
685 void ASTDeclWriter::VisitUsingDecl(UsingDecl
*D
) {
687 Writer
.AddSourceRange(D
->getNestedNameRange(), Record
);
688 Writer
.AddSourceLocation(D
->getUsingLocation(), Record
);
689 Writer
.AddNestedNameSpecifier(D
->getTargetNestedNameDecl(), Record
);
690 Writer
.AddDeclarationNameLoc(D
->DNLoc
, D
->getDeclName(), Record
);
691 Writer
.AddDeclRef(D
->FirstUsingShadow
, Record
);
692 Record
.push_back(D
->isTypeName());
693 Writer
.AddDeclRef(Context
.getInstantiatedFromUsingDecl(D
), Record
);
694 Code
= serialization::DECL_USING
;
697 void ASTDeclWriter::VisitUsingShadowDecl(UsingShadowDecl
*D
) {
699 Writer
.AddDeclRef(D
->getTargetDecl(), Record
);
700 Writer
.AddDeclRef(D
->UsingOrNextShadow
, Record
);
701 Writer
.AddDeclRef(Context
.getInstantiatedFromUsingShadowDecl(D
), Record
);
702 Code
= serialization::DECL_USING_SHADOW
;
705 void ASTDeclWriter::VisitUsingDirectiveDecl(UsingDirectiveDecl
*D
) {
707 Writer
.AddSourceLocation(D
->getUsingLoc(), Record
);
708 Writer
.AddSourceLocation(D
->getNamespaceKeyLocation(), Record
);
709 Writer
.AddSourceRange(D
->getQualifierRange(), Record
);
710 Writer
.AddNestedNameSpecifier(D
->getQualifier(), Record
);
711 Writer
.AddDeclRef(D
->getNominatedNamespace(), Record
);
712 Writer
.AddDeclRef(dyn_cast
<Decl
>(D
->getCommonAncestor()), Record
);
713 Code
= serialization::DECL_USING_DIRECTIVE
;
716 void ASTDeclWriter::VisitUnresolvedUsingValueDecl(UnresolvedUsingValueDecl
*D
) {
718 Writer
.AddSourceRange(D
->getTargetNestedNameRange(), Record
);
719 Writer
.AddSourceLocation(D
->getUsingLoc(), Record
);
720 Writer
.AddNestedNameSpecifier(D
->getTargetNestedNameSpecifier(), Record
);
721 Writer
.AddDeclarationNameLoc(D
->DNLoc
, D
->getDeclName(), Record
);
722 Code
= serialization::DECL_UNRESOLVED_USING_VALUE
;
725 void ASTDeclWriter::VisitUnresolvedUsingTypenameDecl(
726 UnresolvedUsingTypenameDecl
*D
) {
728 Writer
.AddSourceRange(D
->getTargetNestedNameRange(), Record
);
729 Writer
.AddSourceLocation(D
->getUsingLoc(), Record
);
730 Writer
.AddSourceLocation(D
->getTypenameLoc(), Record
);
731 Writer
.AddNestedNameSpecifier(D
->getTargetNestedNameSpecifier(), Record
);
732 Code
= serialization::DECL_UNRESOLVED_USING_TYPENAME
;
735 void ASTDeclWriter::VisitCXXRecordDecl(CXXRecordDecl
*D
) {
738 CXXRecordDecl
*DefinitionDecl
= 0;
739 if (D
->DefinitionData
)
740 DefinitionDecl
= D
->DefinitionData
->Definition
;
741 Writer
.AddDeclRef(DefinitionDecl
, Record
);
742 if (D
== DefinitionDecl
)
743 Writer
.AddCXXDefinitionData(D
, Record
);
746 CXXRecNotTemplate
= 0, CXXRecTemplate
, CXXRecMemberSpecialization
748 if (ClassTemplateDecl
*TemplD
= D
->getDescribedClassTemplate()) {
749 Record
.push_back(CXXRecTemplate
);
750 Writer
.AddDeclRef(TemplD
, Record
);
751 } else if (MemberSpecializationInfo
*MSInfo
752 = D
->getMemberSpecializationInfo()) {
753 Record
.push_back(CXXRecMemberSpecialization
);
754 Writer
.AddDeclRef(MSInfo
->getInstantiatedFrom(), Record
);
755 Record
.push_back(MSInfo
->getTemplateSpecializationKind());
756 Writer
.AddSourceLocation(MSInfo
->getPointOfInstantiation(), Record
);
758 Record
.push_back(CXXRecNotTemplate
);
761 // Store the key function to avoid deserializing every method so we can
764 Writer
.AddDeclRef(Context
.getKeyFunction(D
), Record
);
766 Code
= serialization::DECL_CXX_RECORD
;
769 void ASTDeclWriter::VisitCXXMethodDecl(CXXMethodDecl
*D
) {
770 VisitFunctionDecl(D
);
771 Record
.push_back(D
->size_overridden_methods());
772 for (CXXMethodDecl::method_iterator
773 I
= D
->begin_overridden_methods(), E
= D
->end_overridden_methods();
775 Writer
.AddDeclRef(*I
, Record
);
776 Code
= serialization::DECL_CXX_METHOD
;
779 void ASTDeclWriter::VisitCXXConstructorDecl(CXXConstructorDecl
*D
) {
780 VisitCXXMethodDecl(D
);
782 Record
.push_back(D
->IsExplicitSpecified
);
783 Record
.push_back(D
->ImplicitlyDefined
);
784 Writer
.AddCXXBaseOrMemberInitializers(D
->BaseOrMemberInitializers
,
785 D
->NumBaseOrMemberInitializers
, Record
);
787 Code
= serialization::DECL_CXX_CONSTRUCTOR
;
790 void ASTDeclWriter::VisitCXXDestructorDecl(CXXDestructorDecl
*D
) {
791 VisitCXXMethodDecl(D
);
793 Record
.push_back(D
->ImplicitlyDefined
);
794 Writer
.AddDeclRef(D
->OperatorDelete
, Record
);
796 Code
= serialization::DECL_CXX_DESTRUCTOR
;
799 void ASTDeclWriter::VisitCXXConversionDecl(CXXConversionDecl
*D
) {
800 VisitCXXMethodDecl(D
);
801 Record
.push_back(D
->IsExplicitSpecified
);
802 Code
= serialization::DECL_CXX_CONVERSION
;
805 void ASTDeclWriter::VisitAccessSpecDecl(AccessSpecDecl
*D
) {
807 Writer
.AddSourceLocation(D
->getColonLoc(), Record
);
808 Code
= serialization::DECL_ACCESS_SPEC
;
811 void ASTDeclWriter::VisitFriendDecl(FriendDecl
*D
) {
813 Record
.push_back(D
->Friend
.is
<TypeSourceInfo
*>());
814 if (D
->Friend
.is
<TypeSourceInfo
*>())
815 Writer
.AddTypeSourceInfo(D
->Friend
.get
<TypeSourceInfo
*>(), Record
);
817 Writer
.AddDeclRef(D
->Friend
.get
<NamedDecl
*>(), Record
);
818 Writer
.AddDeclRef(D
->getNextFriend(), Record
);
819 Record
.push_back(D
->UnsupportedFriend
);
820 Writer
.AddSourceLocation(D
->FriendLoc
, Record
);
821 Code
= serialization::DECL_FRIEND
;
824 void ASTDeclWriter::VisitFriendTemplateDecl(FriendTemplateDecl
*D
) {
826 Record
.push_back(D
->getNumTemplateParameters());
827 for (unsigned i
= 0, e
= D
->getNumTemplateParameters(); i
!= e
; ++i
)
828 Writer
.AddTemplateParameterList(D
->getTemplateParameterList(i
), Record
);
829 Record
.push_back(D
->getFriendDecl() != 0);
830 if (D
->getFriendDecl())
831 Writer
.AddDeclRef(D
->getFriendDecl(), Record
);
833 Writer
.AddTypeSourceInfo(D
->getFriendType(), Record
);
834 Writer
.AddSourceLocation(D
->getFriendLoc(), Record
);
835 Code
= serialization::DECL_FRIEND_TEMPLATE
;
838 void ASTDeclWriter::VisitTemplateDecl(TemplateDecl
*D
) {
841 Writer
.AddDeclRef(D
->getTemplatedDecl(), Record
);
842 Writer
.AddTemplateParameterList(D
->getTemplateParameters(), Record
);
845 void ASTDeclWriter::VisitRedeclarableTemplateDecl(RedeclarableTemplateDecl
*D
) {
846 // Emit data to initialize CommonOrPrev before VisitTemplateDecl so that
847 // getCommonPtr() can be used while this is still initializing.
849 Writer
.AddDeclRef(D
->getPreviousDeclaration(), Record
);
850 if (D
->getPreviousDeclaration() == 0) {
851 // This TemplateDecl owns the CommonPtr; write it.
852 assert(D
->isCanonicalDecl());
854 Writer
.AddDeclRef(D
->getInstantiatedFromMemberTemplate(), Record
);
855 if (D
->getInstantiatedFromMemberTemplate())
856 Record
.push_back(D
->isMemberSpecialization());
858 Writer
.AddDeclRef(D
->getCommonPtr()->Latest
, Record
);
860 RedeclarableTemplateDecl
*First
= D
->getFirstDeclaration();
862 // If this is a most recent redeclaration that is pointed to by a first decl
863 // in a chained PCH, keep track of the association with the map so we can
864 // update the first decl during AST reading.
865 if (First
->getMostRecentDeclaration() == D
&&
866 First
->getPCHLevel() > D
->getPCHLevel()) {
867 assert(Writer
.FirstLatestDecls
.find(First
)==Writer
.FirstLatestDecls
.end()
868 && "The latest is already set");
869 Writer
.FirstLatestDecls
[First
] = D
;
873 VisitTemplateDecl(D
);
874 Record
.push_back(D
->getIdentifierNamespace());
877 void ASTDeclWriter::VisitClassTemplateDecl(ClassTemplateDecl
*D
) {
878 VisitRedeclarableTemplateDecl(D
);
880 if (D
->getPreviousDeclaration() == 0) {
881 typedef llvm::FoldingSet
<ClassTemplateSpecializationDecl
> CTSDSetTy
;
882 CTSDSetTy
&CTSDSet
= D
->getSpecializations();
883 Record
.push_back(CTSDSet
.size());
884 for (CTSDSetTy::iterator I
=CTSDSet
.begin(), E
= CTSDSet
.end(); I
!=E
; ++I
) {
885 assert(I
->isCanonicalDecl() && "Expected only canonical decls in set");
886 Writer
.AddDeclRef(&*I
, Record
);
889 typedef llvm::FoldingSet
<ClassTemplatePartialSpecializationDecl
> CTPSDSetTy
;
890 CTPSDSetTy
&CTPSDSet
= D
->getPartialSpecializations();
891 Record
.push_back(CTPSDSet
.size());
892 for (CTPSDSetTy::iterator I
=CTPSDSet
.begin(), E
=CTPSDSet
.end(); I
!=E
; ++I
) {
893 assert(I
->isCanonicalDecl() && "Expected only canonical decls in set");
894 Writer
.AddDeclRef(&*I
, Record
);
897 // InjectedClassNameType is computed, no need to write it.
899 Code
= serialization::DECL_CLASS_TEMPLATE
;
902 void ASTDeclWriter::VisitClassTemplateSpecializationDecl(
903 ClassTemplateSpecializationDecl
*D
) {
904 VisitCXXRecordDecl(D
);
906 llvm::PointerUnion
<ClassTemplateDecl
*,
907 ClassTemplatePartialSpecializationDecl
*> InstFrom
908 = D
->getSpecializedTemplateOrPartial();
910 if (InstFrom
.is
<ClassTemplateDecl
*>()) {
911 InstFromD
= InstFrom
.get
<ClassTemplateDecl
*>();
912 Writer
.AddDeclRef(InstFromD
, Record
);
914 InstFromD
= InstFrom
.get
<ClassTemplatePartialSpecializationDecl
*>();
915 Writer
.AddDeclRef(InstFromD
, Record
);
916 Writer
.AddTemplateArgumentList(&D
->getTemplateInstantiationArgs(), Record
);
917 InstFromD
= cast
<ClassTemplatePartialSpecializationDecl
>(InstFromD
)->
918 getSpecializedTemplate();
922 Writer
.AddTypeSourceInfo(D
->getTypeAsWritten(), Record
);
923 if (D
->getTypeAsWritten()) {
924 Writer
.AddSourceLocation(D
->getExternLoc(), Record
);
925 Writer
.AddSourceLocation(D
->getTemplateKeywordLoc(), Record
);
928 Writer
.AddTemplateArgumentList(&D
->getTemplateArgs(), Record
);
929 Writer
.AddSourceLocation(D
->getPointOfInstantiation(), Record
);
930 Record
.push_back(D
->getSpecializationKind());
932 if (D
->isCanonicalDecl()) {
933 // When reading, we'll add it to the folding set of the following template.
934 Writer
.AddDeclRef(D
->getSpecializedTemplate()->getCanonicalDecl(), Record
);
937 Code
= serialization::DECL_CLASS_TEMPLATE_SPECIALIZATION
;
940 void ASTDeclWriter::VisitClassTemplatePartialSpecializationDecl(
941 ClassTemplatePartialSpecializationDecl
*D
) {
942 VisitClassTemplateSpecializationDecl(D
);
944 Writer
.AddTemplateParameterList(D
->getTemplateParameters(), Record
);
946 Record
.push_back(D
->getNumTemplateArgsAsWritten());
947 for (int i
= 0, e
= D
->getNumTemplateArgsAsWritten(); i
!= e
; ++i
)
948 Writer
.AddTemplateArgumentLoc(D
->getTemplateArgsAsWritten()[i
], Record
);
950 Record
.push_back(D
->getSequenceNumber());
952 // These are read/set from/to the first declaration.
953 if (D
->getPreviousDeclaration() == 0) {
954 Writer
.AddDeclRef(D
->getInstantiatedFromMember(), Record
);
955 Record
.push_back(D
->isMemberSpecialization());
958 Code
= serialization::DECL_CLASS_TEMPLATE_PARTIAL_SPECIALIZATION
;
961 void ASTDeclWriter::VisitFunctionTemplateDecl(FunctionTemplateDecl
*D
) {
962 VisitRedeclarableTemplateDecl(D
);
964 if (D
->getPreviousDeclaration() == 0) {
965 // This FunctionTemplateDecl owns the CommonPtr; write it.
967 // Write the function specialization declarations.
968 Record
.push_back(D
->getSpecializations().size());
969 for (llvm::FoldingSet
<FunctionTemplateSpecializationInfo
>::iterator
970 I
= D
->getSpecializations().begin(),
971 E
= D
->getSpecializations().end() ; I
!= E
; ++I
) {
972 assert(I
->Function
->isCanonicalDecl() &&
973 "Expected only canonical decls in set");
974 Writer
.AddDeclRef(I
->Function
, Record
);
977 Code
= serialization::DECL_FUNCTION_TEMPLATE
;
980 void ASTDeclWriter::VisitTemplateTypeParmDecl(TemplateTypeParmDecl
*D
) {
983 Record
.push_back(D
->wasDeclaredWithTypename());
984 Record
.push_back(D
->isParameterPack());
985 Record
.push_back(D
->defaultArgumentWasInherited());
986 Writer
.AddTypeSourceInfo(D
->getDefaultArgumentInfo(), Record
);
988 Code
= serialization::DECL_TEMPLATE_TYPE_PARM
;
991 void ASTDeclWriter::VisitNonTypeTemplateParmDecl(NonTypeTemplateParmDecl
*D
) {
993 // TemplateParmPosition.
994 Record
.push_back(D
->getDepth());
995 Record
.push_back(D
->getPosition());
996 // Rest of NonTypeTemplateParmDecl.
997 Record
.push_back(D
->getDefaultArgument() != 0);
998 if (D
->getDefaultArgument()) {
999 Writer
.AddStmt(D
->getDefaultArgument());
1000 Record
.push_back(D
->defaultArgumentWasInherited());
1002 Code
= serialization::DECL_NON_TYPE_TEMPLATE_PARM
;
1005 void ASTDeclWriter::VisitTemplateTemplateParmDecl(TemplateTemplateParmDecl
*D
) {
1006 VisitTemplateDecl(D
);
1007 // TemplateParmPosition.
1008 Record
.push_back(D
->getDepth());
1009 Record
.push_back(D
->getPosition());
1010 // Rest of TemplateTemplateParmDecl.
1011 Writer
.AddTemplateArgumentLoc(D
->getDefaultArgument(), Record
);
1012 Record
.push_back(D
->defaultArgumentWasInherited());
1013 Code
= serialization::DECL_TEMPLATE_TEMPLATE_PARM
;
1016 void ASTDeclWriter::VisitStaticAssertDecl(StaticAssertDecl
*D
) {
1018 Writer
.AddStmt(D
->getAssertExpr());
1019 Writer
.AddStmt(D
->getMessage());
1020 Code
= serialization::DECL_STATIC_ASSERT
;
1023 /// \brief Emit the DeclContext part of a declaration context decl.
1025 /// \param LexicalOffset the offset at which the DECL_CONTEXT_LEXICAL
1026 /// block for this declaration context is stored. May be 0 to indicate
1027 /// that there are no declarations stored within this context.
1029 /// \param VisibleOffset the offset at which the DECL_CONTEXT_VISIBLE
1030 /// block for this declaration context is stored. May be 0 to indicate
1031 /// that there are no declarations visible from this context. Note
1032 /// that this value will not be emitted for non-primary declaration
1034 void ASTDeclWriter::VisitDeclContext(DeclContext
*DC
, uint64_t LexicalOffset
,
1035 uint64_t VisibleOffset
) {
1036 Record
.push_back(LexicalOffset
);
1037 Record
.push_back(VisibleOffset
);
1040 template <typename T
>
1041 void ASTDeclWriter::VisitRedeclarable(Redeclarable
<T
> *D
) {
1042 enum { NoRedeclaration
= 0, PointsToPrevious
, PointsToLatest
};
1043 if (D
->RedeclLink
.getNext() == D
) {
1044 Record
.push_back(NoRedeclaration
);
1046 Record
.push_back(D
->RedeclLink
.NextIsPrevious() ? PointsToPrevious
1048 Writer
.AddDeclRef(D
->RedeclLink
.getPointer(), Record
);
1051 T
*First
= D
->getFirstDeclaration();
1052 T
*ThisDecl
= static_cast<T
*>(D
);
1053 // If this is a most recent redeclaration that is pointed to by a first decl
1054 // in a chained PCH, keep track of the association with the map so we can
1055 // update the first decl during AST reading.
1056 if (ThisDecl
!= First
&& First
->getMostRecentDeclaration() == ThisDecl
&&
1057 First
->getPCHLevel() > ThisDecl
->getPCHLevel()) {
1058 assert(Writer
.FirstLatestDecls
.find(First
) == Writer
.FirstLatestDecls
.end()
1059 && "The latest is already set");
1060 Writer
.FirstLatestDecls
[First
] = ThisDecl
;
1064 //===----------------------------------------------------------------------===//
1065 // ASTWriter Implementation
1066 //===----------------------------------------------------------------------===//
1068 void ASTWriter::WriteDeclsBlockAbbrevs() {
1069 using namespace llvm
;
1070 // Abbreviation for DECL_PARM_VAR.
1071 BitCodeAbbrev
*Abv
= new BitCodeAbbrev();
1072 Abv
->Add(BitCodeAbbrevOp(serialization::DECL_PARM_VAR
));
1075 Abv
->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR
, 6)); // DeclContext
1076 Abv
->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR
, 6)); // LexicalDeclContext
1077 Abv
->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR
, 6)); // Location
1078 Abv
->Add(BitCodeAbbrevOp(0)); // isInvalidDecl (!?)
1079 Abv
->Add(BitCodeAbbrevOp(0)); // HasAttrs
1080 Abv
->Add(BitCodeAbbrevOp(0)); // isImplicit
1081 Abv
->Add(BitCodeAbbrevOp(0)); // isUsed
1082 Abv
->Add(BitCodeAbbrevOp(AS_none
)); // C++ AccessSpecifier
1083 Abv
->Add(BitCodeAbbrevOp(0)); // PCH level
1086 Abv
->Add(BitCodeAbbrevOp(0)); // NameKind = Identifier
1087 Abv
->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR
, 6)); // Name
1089 Abv
->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::VBR
, 6)); // Type
1091 Abv
->Add(BitCodeAbbrevOp(0)); // hasExtInfo
1092 Abv
->Add(BitCodeAbbrevOp(serialization::PREDEF_TYPE_NULL_ID
)); // InfoType
1094 Abv
->Add(BitCodeAbbrevOp(0)); // No redeclaration
1095 Abv
->Add(BitCodeAbbrevOp(0)); // StorageClass
1096 Abv
->Add(BitCodeAbbrevOp(0)); // StorageClassAsWritten
1097 Abv
->Add(BitCodeAbbrevOp(0)); // isThreadSpecified
1098 Abv
->Add(BitCodeAbbrevOp(0)); // hasCXXDirectInitializer
1099 Abv
->Add(BitCodeAbbrevOp(0)); // isExceptionVariable
1100 Abv
->Add(BitCodeAbbrevOp(0)); // isNRVOVariable
1101 Abv
->Add(BitCodeAbbrevOp(0)); // HasInit
1102 Abv
->Add(BitCodeAbbrevOp(0)); // HasMemberSpecializationInfo
1104 Abv
->Add(BitCodeAbbrevOp(0)); // ObjCDeclQualifier
1105 Abv
->Add(BitCodeAbbrevOp(0)); // HasInheritedDefaultArg
1106 Abv
->Add(BitCodeAbbrevOp(0)); // HasUninstantiatedDefaultArg
1108 ParmVarDeclAbbrev
= Stream
.EmitAbbrev(Abv
);
1110 Abv
= new BitCodeAbbrev();
1111 Abv
->Add(BitCodeAbbrevOp(serialization::DECL_CONTEXT_LEXICAL
));
1112 Abv
->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob
));
1113 DeclContextLexicalAbbrev
= Stream
.EmitAbbrev(Abv
);
1115 Abv
= new BitCodeAbbrev();
1116 Abv
->Add(BitCodeAbbrevOp(serialization::DECL_CONTEXT_VISIBLE
));
1117 Abv
->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Fixed
, 32));
1118 Abv
->Add(BitCodeAbbrevOp(BitCodeAbbrevOp::Blob
));
1119 DeclContextVisibleLookupAbbrev
= Stream
.EmitAbbrev(Abv
);
1122 /// isRequiredDecl - Check if this is a "required" Decl, which must be seen by
1123 /// consumers of the AST.
1125 /// Such decls will always be deserialized from the AST file, so we would like
1126 /// this to be as restrictive as possible. Currently the predicate is driven by
1127 /// code generation requirements, if other clients have a different notion of
1128 /// what is "required" then we may have to consider an alternate scheme where
1129 /// clients can iterate over the top-level decls and get information on them,
1130 /// without necessary deserializing them. We could explicitly require such
1131 /// clients to use a separate API call to "realize" the decl. This should be
1132 /// relatively painless since they would presumably only do it for top-level
1134 static bool isRequiredDecl(const Decl
*D
, ASTContext
&Context
) {
1135 // File scoped assembly or obj-c implementation must be seen.
1136 if (isa
<FileScopeAsmDecl
>(D
) || isa
<ObjCImplementationDecl
>(D
))
1139 return Context
.DeclMustBeEmitted(D
);
1142 void ASTWriter::WriteDecl(ASTContext
&Context
, Decl
*D
) {
1143 // Switch case IDs are per Decl.
1144 ClearSwitchCaseIDs();
1147 ASTDeclWriter
W(*this, Context
, Record
);
1149 // If this declaration is also a DeclContext, write blocks for the
1150 // declarations that lexically stored inside its context and those
1151 // declarations that are visible from its context. These blocks
1152 // are written before the declaration itself so that we can put
1153 // their offsets into the record for the declaration.
1154 uint64_t LexicalOffset
= 0;
1155 uint64_t VisibleOffset
= 0;
1156 DeclContext
*DC
= dyn_cast
<DeclContext
>(D
);
1158 LexicalOffset
= WriteDeclContextLexicalBlock(Context
, DC
);
1159 VisibleOffset
= WriteDeclContextVisibleBlock(Context
, DC
);
1162 // Determine the ID for this declaration
1163 serialization::DeclID
&IDR
= DeclIDs
[D
];
1166 serialization::DeclID ID
= IDR
;
1168 if (ID
< FirstDeclID
) {
1169 // We're replacing a decl in a previous file.
1170 ReplacedDecls
.push_back(std::make_pair(ID
, Stream
.GetCurrentBitNo()));
1172 unsigned Index
= ID
- FirstDeclID
;
1174 // Record the offset for this declaration
1175 if (DeclOffsets
.size() == Index
)
1176 DeclOffsets
.push_back(Stream
.GetCurrentBitNo());
1177 else if (DeclOffsets
.size() < Index
) {
1178 DeclOffsets
.resize(Index
+1);
1179 DeclOffsets
[Index
] = Stream
.GetCurrentBitNo();
1183 // Build and emit a record for this declaration
1185 W
.Code
= (serialization::DeclCode
)0;
1188 if (DC
) W
.VisitDeclContext(DC
, LexicalOffset
, VisibleOffset
);
1191 llvm::report_fatal_error(llvm::StringRef("unexpected declaration kind '") +
1192 D
->getDeclKindName() + "'");
1193 Stream
.EmitRecord(W
.Code
, Record
, W
.AbbrevToUse
);
1195 // Flush any expressions that were written as part of this declaration.
1198 // Flush C++ base specifiers, if there are any.
1199 FlushCXXBaseSpecifiers();
1201 // Note "external" declarations so that we can add them to a record in the
1204 // FIXME: This should be renamed, the predicate is much more complicated.
1205 if (isRequiredDecl(D
, Context
))
1206 ExternalDefinitions
.push_back(ID
);