-//===--- ASTContext.h - Context to hold long-lived AST nodes ----*- C++ -*-===//
+//===- ASTContext.h - Context to hold long-lived AST nodes ------*- C++ -*-===//
//
// The LLVM Compiler Infrastructure
//
// License. See LICENSE.TXT for details.
//
//===----------------------------------------------------------------------===//
-///
+//
/// \file
/// \brief Defines the clang::ASTContext interface.
-///
+//
//===----------------------------------------------------------------------===//
#ifndef LLVM_CLANG_AST_ASTCONTEXT_H
#include "clang/AST/CanonicalType.h"
#include "clang/AST/CommentCommandTraits.h"
#include "clang/AST/Decl.h"
-#include "clang/AST/DeclarationName.h"
#include "clang/AST/DeclBase.h"
+#include "clang/AST/DeclarationName.h"
#include "clang/AST/ExternalASTSource.h"
#include "clang/AST/NestedNameSpecifier.h"
#include "clang/AST/PrettyPrinter.h"
#include "clang/AST/Type.h"
#include "clang/Basic/AddressSpaces.h"
#include "clang/Basic/IdentifierTable.h"
+#include "clang/Basic/LLVM.h"
#include "clang/Basic/LangOptions.h"
#include "clang/Basic/Linkage.h"
-#include "clang/Basic/LLVM.h"
-#include "clang/Basic/Module.h"
#include "clang/Basic/OperatorKinds.h"
#include "clang/Basic/PartialDiagnostic.h"
#include "clang/Basic/SanitizerBlacklist.h"
#include "llvm/ADT/DenseMap.h"
#include "llvm/ADT/FoldingSet.h"
#include "llvm/ADT/IntrusiveRefCntPtr.h"
-#include "llvm/ADT/iterator_range.h"
#include "llvm/ADT/MapVector.h"
#include "llvm/ADT/None.h"
#include "llvm/ADT/Optional.h"
#include "llvm/ADT/PointerIntPair.h"
#include "llvm/ADT/PointerUnion.h"
-#include "llvm/ADT/SmallPtrSet.h"
#include "llvm/ADT/SmallVector.h"
-#include "llvm/ADT/TinyPtrVector.h"
#include "llvm/ADT/StringMap.h"
#include "llvm/ADT/StringRef.h"
+#include "llvm/ADT/TinyPtrVector.h"
+#include "llvm/ADT/Triple.h"
+#include "llvm/ADT/iterator_range.h"
#include "llvm/Support/AlignOf.h"
#include "llvm/Support/Allocator.h"
#include "llvm/Support/Casting.h"
#include <cstdint>
#include <iterator>
#include <memory>
-#include <new>
#include <string>
#include <type_traits>
#include <utility>
struct fltSemantics;
-} // end namespace llvm
+} // namespace llvm
namespace clang {
+class APValue;
class ASTMutationListener;
class ASTRecordLayout;
class AtomicExpr;
class BlockExpr;
+class BuiltinTemplateDecl;
class CharUnits;
class CXXABI;
+class CXXConstructorDecl;
+class CXXMethodDecl;
+class CXXRecordDecl;
class DiagnosticsEngine;
class Expr;
+class MangleContext;
class MangleNumberingContext;
class MaterializeTemporaryExpr;
-// Decls
-class MangleContext;
+class MemberSpecializationInfo;
+class Module;
+class ObjCCategoryDecl;
+class ObjCCategoryImplDecl;
+class ObjCContainerDecl;
+class ObjCImplDecl;
+class ObjCImplementationDecl;
+class ObjCInterfaceDecl;
class ObjCIvarDecl;
+class ObjCMethodDecl;
class ObjCPropertyDecl;
+class ObjCPropertyImplDecl;
+class ObjCProtocolDecl;
+class ObjCTypeParamDecl;
+class Preprocessor;
+class Stmt;
+class StoredDeclsMap;
+class TemplateDecl;
+class TemplateParameterList;
+class TemplateTemplateParmDecl;
+class TemplateTypeParmDecl;
class UnresolvedSetIterator;
-class UsingDecl;
class UsingShadowDecl;
+class VarTemplateDecl;
class VTableContextBase;
namespace Builtin {
- class Context;
+class Context;
-} // end namespace Builtin
+} // namespace Builtin
enum BuiltinTemplateKind : int;
namespace comments {
- class FullComment;
+class FullComment;
-} // end namespace comments
+} // namespace comments
struct TypeInfo {
- uint64_t Width;
- unsigned Align;
+ uint64_t Width = 0;
+ unsigned Align = 0;
bool AlignIsRequired : 1;
- TypeInfo() : Width(0), Align(0), AlignIsRequired(false) {}
+ TypeInfo() : AlignIsRequired(false) {}
TypeInfo(uint64_t Width, unsigned Align, bool AlignIsRequired)
: Width(Width), Align(Align), AlignIsRequired(AlignIsRequired) {}
};
/// \brief Holds long-lived AST nodes (such as types and decls) that can be
/// referred to throughout the semantic analysis of a file.
class ASTContext : public RefCountedBase<ASTContext> {
- ASTContext &this_() { return *this; }
+ friend class NestedNameSpecifier;
mutable SmallVector<Type *, 0> Types;
mutable llvm::FoldingSet<ExtQuals> ExtQualNodes;
///
/// This set is managed by the NestedNameSpecifier class.
mutable llvm::FoldingSet<NestedNameSpecifier> NestedNameSpecifiers;
- mutable NestedNameSpecifier *GlobalNestedNameSpecifier;
- friend class NestedNameSpecifier;
+ mutable NestedNameSpecifier *GlobalNestedNameSpecifier = nullptr;
/// \brief A cache mapping from RecordDecls to ASTRecordLayouts.
///
ObjCLayouts;
/// \brief A cache from types to size and alignment information.
- typedef llvm::DenseMap<const Type *, struct TypeInfo> TypeInfoMap;
+ using TypeInfoMap = llvm::DenseMap<const Type *, struct TypeInfo>;
mutable TypeInfoMap MemoizedTypeInfo;
/// \brief A cache mapping from CXXRecordDecls to key functions.
public:
CanonicalTemplateTemplateParm(TemplateTemplateParmDecl *Parm)
- : Parm(Parm) { }
+ : Parm(Parm) {}
TemplateTemplateParmDecl *getParam() const { return Parm; }
getCanonicalTemplateTemplateParmDecl(TemplateTemplateParmDecl *TTP) const;
/// \brief The typedef for the __int128_t type.
- mutable TypedefDecl *Int128Decl;
+ mutable TypedefDecl *Int128Decl = nullptr;
/// \brief The typedef for the __uint128_t type.
- mutable TypedefDecl *UInt128Decl;
+ mutable TypedefDecl *UInt128Decl = nullptr;
/// \brief The typedef for the target specific predefined
/// __builtin_va_list type.
- mutable TypedefDecl *BuiltinVaListDecl;
+ mutable TypedefDecl *BuiltinVaListDecl = nullptr;
/// The typedef for the predefined \c __builtin_ms_va_list type.
- mutable TypedefDecl *BuiltinMSVaListDecl;
+ mutable TypedefDecl *BuiltinMSVaListDecl = nullptr;
/// \brief The typedef for the predefined \c id type.
- mutable TypedefDecl *ObjCIdDecl;
+ mutable TypedefDecl *ObjCIdDecl = nullptr;
/// \brief The typedef for the predefined \c SEL type.
- mutable TypedefDecl *ObjCSelDecl;
+ mutable TypedefDecl *ObjCSelDecl = nullptr;
/// \brief The typedef for the predefined \c Class type.
- mutable TypedefDecl *ObjCClassDecl;
+ mutable TypedefDecl *ObjCClassDecl = nullptr;
/// \brief The typedef for the predefined \c Protocol class in Objective-C.
- mutable ObjCInterfaceDecl *ObjCProtocolClassDecl;
+ mutable ObjCInterfaceDecl *ObjCProtocolClassDecl = nullptr;
/// \brief The typedef for the predefined 'BOOL' type.
- mutable TypedefDecl *BOOLDecl;
+ mutable TypedefDecl *BOOLDecl = nullptr;
// Typedefs which may be provided defining the structure of Objective-C
// pseudo-builtins
mutable IdentifierInfo *TypePackElementName = nullptr;
QualType ObjCConstantStringType;
- mutable RecordDecl *CFConstantStringTagDecl;
- mutable TypedefDecl *CFConstantStringTypeDecl;
+ mutable RecordDecl *CFConstantStringTagDecl = nullptr;
+ mutable TypedefDecl *CFConstantStringTypeDecl = nullptr;
mutable QualType ObjCSuperType;
QualType ObjCNSStringType;
/// \brief The typedef declaration for the Objective-C "instancetype" type.
- TypedefDecl *ObjCInstanceTypeDecl;
+ TypedefDecl *ObjCInstanceTypeDecl = nullptr;
/// \brief The type for the C FILE type.
- TypeDecl *FILEDecl;
+ TypeDecl *FILEDecl = nullptr;
/// \brief The type for the C jmp_buf type.
- TypeDecl *jmp_bufDecl;
+ TypeDecl *jmp_bufDecl = nullptr;
/// \brief The type for the C sigjmp_buf type.
- TypeDecl *sigjmp_bufDecl;
+ TypeDecl *sigjmp_bufDecl = nullptr;
/// \brief The type for the C ucontext_t type.
- TypeDecl *ucontext_tDecl;
+ TypeDecl *ucontext_tDecl = nullptr;
/// \brief Type for the Block descriptor for Blocks CodeGen.
///
/// Since this is only used for generation of debug info, it is not
/// serialized.
- mutable RecordDecl *BlockDescriptorType;
+ mutable RecordDecl *BlockDescriptorType = nullptr;
/// \brief Type for the Block descriptor for Blocks CodeGen.
///
/// Since this is only used for generation of debug info, it is not
/// serialized.
- mutable RecordDecl *BlockDescriptorExtendedType;
+ mutable RecordDecl *BlockDescriptorExtendedType = nullptr;
/// \brief Declaration for the CUDA cudaConfigureCall function.
- FunctionDecl *cudaConfigureCallDecl;
+ FunctionDecl *cudaConfigureCallDecl = nullptr;
/// \brief Keeps track of all declaration attributes.
///
};
llvm::DenseMap<Module*, PerModuleInitializers*> ModuleInitializers;
+ ASTContext &this_() { return *this; }
+
public:
/// \brief A type synonym for the TemplateOrInstantiation mapping.
- typedef llvm::PointerUnion<VarTemplateDecl *, MemberSpecializationInfo *>
- TemplateOrSpecializationInfo;
+ using TemplateOrSpecializationInfo =
+ llvm::PointerUnion<VarTemplateDecl *, MemberSpecializationInfo *>;
private:
+ friend class ASTDeclReader;
+ friend class ASTReader;
+ friend class ASTWriter;
+ friend class CXXRecordDecl;
+
/// \brief A mapping to contain the template or declaration that
/// a variable declaration describes or was instantiated from,
/// respectively.
/// Since most C++ member functions aren't virtual and therefore
/// don't override anything, we store the overridden functions in
/// this map on the side rather than within the CXXMethodDecl structure.
- typedef llvm::TinyPtrVector<const CXXMethodDecl*> CXXMethodVector;
+ using CXXMethodVector = llvm::TinyPtrVector<const CXXMethodDecl *>;
llvm::DenseMap<const CXXMethodDecl *, CXXMethodVector> OverriddenMethods;
/// \brief Mapping from each declaration context to its corresponding
/// \brief Mapping that stores parameterIndex values for ParmVarDecls when
/// that value exceeds the bitfield size of ParmVarDeclBits.ParameterIndex.
- typedef llvm::DenseMap<const VarDecl *, unsigned> ParameterIndexTable;
+ using ParameterIndexTable = llvm::DenseMap<const VarDecl *, unsigned>;
ParameterIndexTable ParamIndices;
- ImportDecl *FirstLocalImport;
- ImportDecl *LastLocalImport;
+ ImportDecl *FirstLocalImport = nullptr;
+ ImportDecl *LastLocalImport = nullptr;
TranslationUnitDecl *TUDecl;
- mutable ExternCContextDecl *ExternCContext;
- mutable BuiltinTemplateDecl *MakeIntegerSeqDecl;
- mutable BuiltinTemplateDecl *TypePackElementDecl;
+ mutable ExternCContextDecl *ExternCContext = nullptr;
+ mutable BuiltinTemplateDecl *MakeIntegerSeqDecl = nullptr;
+ mutable BuiltinTemplateDecl *TypePackElementDecl = nullptr;
/// \brief The associated SourceManager object.
SourceManager &SourceMgr;
CXXABI *createCXXABI(const TargetInfo &T);
/// \brief The logical -> physical address space map.
- const LangASMap *AddrSpaceMap;
+ const LangASMap *AddrSpaceMap = nullptr;
/// \brief Address space map mangling must be used with language specific
/// address spaces (e.g. OpenCL/CUDA)
bool AddrSpaceMapMangling;
- friend class ASTDeclReader;
- friend class ASTReader;
- friend class ASTWriter;
- friend class CXXRecordDecl;
-
- const TargetInfo *Target;
- const TargetInfo *AuxTarget;
+ const TargetInfo *Target = nullptr;
+ const TargetInfo *AuxTarget = nullptr;
clang::PrintingPolicy PrintingPolicy;
public:
Builtin::Context &BuiltinInfo;
mutable DeclarationNameTable DeclarationNames;
IntrusiveRefCntPtr<ExternalASTSource> ExternalSource;
- ASTMutationListener *Listener;
+ ASTMutationListener *Listener = nullptr;
/// \brief Contains parents of a node.
- typedef llvm::SmallVector<ast_type_traits::DynTypedNode, 2> ParentVector;
+ using ParentVector = llvm::SmallVector<ast_type_traits::DynTypedNode, 2>;
/// \brief Maps from a node to its parents. This is used for nodes that have
/// pointer identity only, which are more common and we can save space by
/// only storing a unique pointer to them.
- typedef llvm::DenseMap<const void *,
- llvm::PointerUnion4<const Decl *, const Stmt *,
- ast_type_traits::DynTypedNode *,
- ParentVector *>> ParentMapPointers;
+ using ParentMapPointers =
+ llvm::DenseMap<const void *,
+ llvm::PointerUnion4<const Decl *, const Stmt *,
+ ast_type_traits::DynTypedNode *,
+ ParentVector *>>;
/// Parent map for nodes without pointer identity. We store a full
/// DynTypedNode for all keys.
- typedef llvm::DenseMap<
- ast_type_traits::DynTypedNode,
- llvm::PointerUnion4<const Decl *, const Stmt *,
- ast_type_traits::DynTypedNode *, ParentVector *>>
- ParentMapOtherNodes;
+ using ParentMapOtherNodes =
+ llvm::DenseMap<ast_type_traits::DynTypedNode,
+ llvm::PointerUnion4<const Decl *, const Stmt *,
+ ast_type_traits::DynTypedNode *,
+ ParentVector *>>;
/// Container for either a single DynTypedNode or for an ArrayRef to
/// DynTypedNode. For use with ParentMap.
class DynTypedNodeList {
- typedef ast_type_traits::DynTypedNode DynTypedNode;
+ using DynTypedNode = ast_type_traits::DynTypedNode;
+
llvm::AlignedCharArrayUnion<ast_type_traits::DynTypedNode,
ArrayRef<DynTypedNode>> Storage;
bool IsSingleNode;
DynTypedNodeList(const DynTypedNode &N) : IsSingleNode(true) {
new (Storage.buffer) DynTypedNode(N);
}
+
DynTypedNodeList(ArrayRef<DynTypedNode> A) : IsSingleNode(false) {
new (Storage.buffer) ArrayRef<DynTypedNode>(A);
}
template <typename T> T *Allocate(size_t Num = 1) const {
return static_cast<T *>(Allocate(Num * sizeof(T), alignof(T)));
}
- void Deallocate(void *Ptr) const { }
+ void Deallocate(void *Ptr) const {}
/// Return the total amount of physical memory allocated for representing
/// AST nodes and type information.
size_t getASTAllocatedMemory() const {
return BumpAlloc.getTotalMemory();
}
+
/// Return the total memory used for various side tables.
size_t getSideTableAllocatedMemory() const;
/// Returns empty type if there is no appropriate target types.
QualType getIntTypeForBitwidth(unsigned DestWidth,
unsigned Signed) const;
+
/// getRealTypeForBitwidth -
/// sets floating point QualTy according to specified bitwidth.
/// Returns empty type if there is no appropriate target types.
RawCommentList Comments;
/// \brief True if comments are already loaded from ExternalASTSource.
- mutable bool CommentsLoaded;
+ mutable bool CommentsLoaded = false;
class RawCommentAndCacheFlags {
public:
}
/// \brief Return the documentation comment attached to a given declaration.
- /// Returns NULL if no comment is attached.
+ /// Returns nullptr if no comment is attached.
///
- /// \param OriginalDecl if not NULL, is set to declaration AST node that had
- /// the comment, if the comment we found comes from a redeclaration.
+ /// \param OriginalDecl if not nullptr, is set to declaration AST node that
+ /// had the comment, if the comment we found comes from a redeclaration.
const RawComment *
getRawCommentForAnyRedecl(const Decl *D,
const Decl **OriginalDecl = nullptr) const;
/// Return parsed documentation comment attached to a given declaration.
- /// Returns NULL if no comment is attached.
+ /// Returns nullptr if no comment is attached.
///
- /// \param PP the Preprocessor used with this TU. Could be NULL if
+ /// \param PP the Preprocessor used with this TU. Could be nullptr if
/// preprocessor is not available.
comments::FullComment *getCommentForDecl(const Decl *D,
const Preprocessor *PP) const;
/// Return parsed documentation comment attached to a given declaration.
- /// Returns NULL if no comment is attached. Does not look at any
+ /// Returns nullptr if no comment is attached. Does not look at any
/// redeclarations of the declaration.
comments::FullComment *getLocalCommentForDeclUncached(const Decl *D) const;
/// \brief Iterator that visits import declarations.
class import_iterator {
- ImportDecl *Import;
+ ImportDecl *Import = nullptr;
public:
- typedef ImportDecl *value_type;
- typedef ImportDecl *reference;
- typedef ImportDecl *pointer;
- typedef int difference_type;
- typedef std::forward_iterator_tag iterator_category;
+ using value_type = ImportDecl *;
+ using reference = ImportDecl *;
+ using pointer = ImportDecl *;
+ using difference_type = int;
+ using iterator_category = std::forward_iterator_tag;
- import_iterator() : Import() {}
+ import_iterator() = default;
explicit import_iterator(ImportDecl *Import) : Import(Import) {}
reference operator*() const { return Import; }
void setInstantiatedFromUnnamedFieldDecl(FieldDecl *Inst, FieldDecl *Tmpl);
// Access to the set of methods overridden by the given C++ method.
- typedef CXXMethodVector::const_iterator overridden_cxx_method_iterator;
+ using overridden_cxx_method_iterator = CXXMethodVector::const_iterator;
overridden_cxx_method_iterator
overridden_methods_begin(const CXXMethodDecl *Method) const;
overridden_methods_end(const CXXMethodDecl *Method) const;
unsigned overridden_methods_size(const CXXMethodDecl *Method) const;
- typedef llvm::iterator_range<overridden_cxx_method_iterator>
- overridden_method_range;
+
+ using overridden_method_range =
+ llvm::iterator_range<overridden_cxx_method_iterator>;
+
overridden_method_range overridden_methods(const CXXMethodDecl *Method) const;
/// \brief Note that the given C++ \p Method overrides the given \p
return Import->NextLocalImport;
}
- typedef llvm::iterator_range<import_iterator> import_range;
+ using import_range = llvm::iterator_range<import_iterator>;
+
import_range local_imports() const {
return import_range(import_iterator(FirstLocalImport), import_iterator());
}
/// and should be visible whenever \p M is visible.
void mergeDefinitionIntoModule(NamedDecl *ND, Module *M,
bool NotifyListeners = true);
+
/// \brief Clean up the merged definition list. Call this if you might have
/// added duplicates into the list.
void deduplicateMergedDefinitonsFor(NamedDecl *ND);
/// \brief Return a read_only pipe type for the specified type.
QualType getReadPipeType(QualType T) const;
+
/// \brief Return a write_only pipe type for the specified type.
QualType getWritePipeType(QualType T) const;
void setcudaConfigureCallDecl(FunctionDecl *FD) {
cudaConfigureCallDecl = FD;
}
+
FunctionDecl *getcudaConfigureCallDecl() {
return cudaConfigureCallDecl;
}
/// Returns true iff we need copy/dispose helpers for the given type.
bool BlockRequiresCopying(QualType Ty, const VarDecl *D);
-
/// Returns true, if given type has a known lifetime. HasByrefExtendedLayout is set
/// to false in this case. If HasByrefExtendedLayout returns true, byref variable
/// has extended lifetime.
QualType Canonical = QualType()) const;
bool ObjCObjectAdoptsQTypeProtocols(QualType QT, ObjCInterfaceDecl *Decl);
+
/// QIdProtocolsAdoptObjCObjectProtocols - Checks that protocols in
/// QT's qualified-id protocol list adopt all protocols in IDecl's list
/// of protocols.
const TemplateArgument &ArgPack) const;
enum GetBuiltinTypeError {
- GE_None, ///< No error
- GE_Missing_stdio, ///< Missing a type from <stdio.h>
- GE_Missing_setjmp, ///< Missing a type from <setjmp.h>
- GE_Missing_ucontext ///< Missing a type from <ucontext.h>
+ /// No error
+ GE_None,
+
+ /// Missing a type from <stdio.h>
+ GE_Missing_stdio,
+
+ /// Missing a type from <setjmp.h>
+ GE_Missing_setjmp,
+
+ /// Missing a type from <ucontext.h>
+ GE_Missing_ucontext
};
/// \brief Return the type for the specified builtin.
getASTObjCImplementationLayout(const ObjCImplementationDecl *D) const;
/// \brief Get our current best idea for the key function of the
- /// given record decl, or NULL if there isn't one.
+ /// given record decl, or nullptr if there isn't one.
///
/// The key function is, according to the Itanium C++ ABI section 5.2.3:
/// ...the first non-pure virtual function that is not inline at the
bool hasSameType(QualType T1, QualType T2) const {
return getCanonicalType(T1) == getCanonicalType(T2);
}
-
bool hasSameType(const Type *T1, const Type *T2) const {
return getCanonicalType(T1) == getCanonicalType(T2);
}
bool isObjCIdType(QualType T) const {
return T == getObjCIdType();
}
+
bool isObjCClassType(QualType T) const {
return T == getObjCClassType();
}
+
bool isObjCSelType(QualType T) const {
return T == getObjCSelType();
}
+
bool ObjCQualifiedIdTypesAreCompatible(QualType LHS, QualType RHS,
bool ForCompare);
bool isSentinelNullExpr(const Expr *E);
- /// \brief Get the implementation of the ObjCInterfaceDecl \p D, or NULL if
+ /// \brief Get the implementation of the ObjCInterfaceDecl \p D, or nullptr if
/// none exists.
ObjCImplementationDecl *getObjCImplementation(ObjCInterfaceDecl *D);
- /// \brief Get the implementation of the ObjCCategoryDecl \p D, or NULL if
+
+ /// \brief Get the implementation of the ObjCCategoryDecl \p D, or nullptr if
/// none exists.
- ObjCCategoryImplDecl *getObjCImplementation(ObjCCategoryDecl *D);
+ ObjCCategoryImplDecl *getObjCImplementation(ObjCCategoryDecl *D);
/// \brief Return true if there is at least one \@implementation in the TU.
bool AnyObjCImplementation() {
/// \brief Set the implementation of ObjCInterfaceDecl.
void setObjCImplementation(ObjCInterfaceDecl *IFaceD,
ObjCImplementationDecl *ImplD);
+
/// \brief Set the implementation of ObjCCategoryDecl.
void setObjCImplementation(ObjCCategoryDecl *CatD,
ObjCCategoryImplDecl *ImplD);
/// \brief Set the copy inialization expression of a block var decl.
void setBlockVarCopyInits(VarDecl*VD, Expr* Init);
+
/// \brief Get the copy initialization expression of the VarDecl \p VD, or
- /// NULL if none exists.
+ /// nullptr if none exists.
Expr *getBlockVarCopyInits(const VarDecl* VD);
/// \brief Allocate an uninitialized TypeSourceInfo.
const FieldDecl *Field,
bool includeVBases = true,
QualType *NotEncodedT=nullptr) const;
+
public:
// Adds the encoding of a method parameter or return type.
void getObjCEncodingForMethodParameter(Decl::ObjCDeclQualifier QT,
bool isMSStaticDataMemberInlineDefinition(const VarDecl *VD) const;
enum class InlineVariableDefinitionKind {
- None, ///< Not an inline variable.
- Weak, ///< Weak definition of inline variable.
- WeakUnknown, ///< Weak for now, might become strong later in this TU.
- Strong ///< Strong definition.
+ /// Not an inline variable.
+ None,
+
+ /// Weak definition of inline variable.
+ Weak,
+
+ /// Weak for now, might become strong later in this TU.
+ WeakUnknown,
+
+ /// Strong definition.
+ Strong
};
+
/// \brief Determine whether a definition of this inline variable should
/// be treated as a weak or strong definition. For compatibility with
/// C++14 and before, for a constexpr static data member, if there is an
getInlineVariableDefinitionKind(const VarDecl *VD) const;
private:
+ friend class DeclarationNameTable;
+ friend class DeclContext;
+
const ASTRecordLayout &
getObjCLayout(const ObjCInterfaceDecl *D,
const ObjCImplementationDecl *Impl) const;
// into the datastructures which avoids this mess during deallocation but is
// wasteful of memory, and here we require a lot of error prone book keeping
// in order to track and run destructors while we're tearing things down.
- typedef llvm::SmallVector<std::pair<void (*)(void *), void *>, 16>
- DeallocationFunctionsAndArguments;
+ using DeallocationFunctionsAndArguments =
+ llvm::SmallVector<std::pair<void (*)(void *), void *>, 16>;
DeallocationFunctionsAndArguments Deallocations;
// FIXME: This currently contains the set of StoredDeclMaps used
// by DeclContext objects. This probably should not be in ASTContext,
// but we include it here so that ASTContext can quickly deallocate them.
- llvm::PointerIntPair<StoredDeclsMap*,1> LastSDM;
-
- friend class DeclContext;
- friend class DeclarationNameTable;
-
- void ReleaseDeclContextMaps();
- void ReleaseParentMapEntries();
+ llvm::PointerIntPair<StoredDeclsMap *, 1> LastSDM;
std::unique_ptr<ParentMapPointers> PointerParents;
std::unique_ptr<ParentMapOtherNodes> OtherParents;
std::unique_ptr<VTableContextBase> VTContext;
+ void ReleaseDeclContextMaps();
+ void ReleaseParentMapEntries();
+
public:
enum PragmaSectionFlag : unsigned {
PSF_None = 0,
SectionInfo(DeclaratorDecl *Decl,
SourceLocation PragmaSectionLocation,
int SectionFlags)
- : Decl(Decl),
- PragmaSectionLocation(PragmaSectionLocation),
- SectionFlags(SectionFlags) {}
+ : Decl(Decl), PragmaSectionLocation(PragmaSectionLocation),
+ SectionFlags(SectionFlags) {}
};
llvm::StringMap<SectionInfo> SectionInfos;
return Ctx.Selectors.getSelector(1, &II);
}
-} // end namespace clang
+} // namespace clang
// operator new and delete aren't allowed inside namespaces.
/// @param C The ASTContext that provides the allocator.
/// @param Alignment The alignment of the allocated memory (if the underlying
/// allocator supports it).
-/// @return The allocated memory. Could be NULL.
+/// @return The allocated memory. Could be nullptr.
inline void *operator new(size_t Bytes, const clang::ASTContext &C,
size_t Alignment) {
return C.Allocate(Bytes, Alignment);
}
+
/// @brief Placement delete companion to the new above.
///
/// This operator is just a companion to the new above. There is no way of
/// @param C The ASTContext that provides the allocator.
/// @param Alignment The alignment of the allocated memory (if the underlying
/// allocator supports it).
-/// @return The allocated memory. Could be NULL.
+/// @return The allocated memory. Could be nullptr.
inline void *operator new[](size_t Bytes, const clang::ASTContext& C,
size_t Alignment = 8) {
return C.Allocate(Bytes, Alignment);
-//===--- ASTContext.cpp - Context to hold long-lived AST nodes ------------===//
+//===- ASTContext.cpp - Context to hold long-lived AST nodes --------------===//
//
// The LLVM Compiler Infrastructure
//
#include "clang/AST/ASTContext.h"
#include "CXXABI.h"
+#include "clang/AST/APValue.h"
#include "clang/AST/ASTMutationListener.h"
+#include "clang/AST/ASTTypeTraits.h"
#include "clang/AST/Attr.h"
+#include "clang/AST/AttrIterator.h"
#include "clang/AST/CharUnits.h"
#include "clang/AST/Comment.h"
-#include "clang/AST/CommentCommandTraits.h"
+#include "clang/AST/Decl.h"
+#include "clang/AST/DeclBase.h"
#include "clang/AST/DeclCXX.h"
#include "clang/AST/DeclContextInternals.h"
#include "clang/AST/DeclObjC.h"
+#include "clang/AST/DeclOpenMP.h"
#include "clang/AST/DeclTemplate.h"
+#include "clang/AST/DeclarationName.h"
#include "clang/AST/Expr.h"
#include "clang/AST/ExprCXX.h"
#include "clang/AST/ExternalASTSource.h"
#include "clang/AST/Mangle.h"
#include "clang/AST/MangleNumberingContext.h"
+#include "clang/AST/NestedNameSpecifier.h"
+#include "clang/AST/RawCommentList.h"
#include "clang/AST/RecordLayout.h"
#include "clang/AST/RecursiveASTVisitor.h"
+#include "clang/AST/Stmt.h"
+#include "clang/AST/TemplateBase.h"
+#include "clang/AST/TemplateName.h"
+#include "clang/AST/Type.h"
#include "clang/AST/TypeLoc.h"
+#include "clang/AST/UnresolvedSet.h"
#include "clang/AST/VTableBuilder.h"
+#include "clang/Basic/AddressSpaces.h"
#include "clang/Basic/Builtins.h"
+#include "clang/Basic/CommentOptions.h"
+#include "clang/Basic/IdentifierTable.h"
+#include "clang/Basic/LLVM.h"
+#include "clang/Basic/LangOptions.h"
+#include "clang/Basic/Linkage.h"
+#include "clang/Basic/ObjCRuntime.h"
+#include "clang/Basic/SanitizerBlacklist.h"
+#include "clang/Basic/SourceLocation.h"
#include "clang/Basic/SourceManager.h"
+#include "clang/Basic/Specifiers.h"
+#include "clang/Basic/TargetCXXABI.h"
#include "clang/Basic/TargetInfo.h"
+#include "clang/Basic/XRayLists.h"
+#include "llvm/ADT/APInt.h"
+#include "llvm/ADT/APSInt.h"
+#include "llvm/ADT/ArrayRef.h"
+#include "llvm/ADT/DenseMap.h"
+#include "llvm/ADT/DenseSet.h"
+#include "llvm/ADT/FoldingSet.h"
+#include "llvm/ADT/None.h"
+#include "llvm/ADT/Optional.h"
+#include "llvm/ADT/PointerUnion.h"
+#include "llvm/ADT/STLExtras.h"
+#include "llvm/ADT/SmallPtrSet.h"
+#include "llvm/ADT/SmallVector.h"
#include "llvm/ADT/StringExtras.h"
+#include "llvm/ADT/StringRef.h"
#include "llvm/ADT/Triple.h"
#include "llvm/Support/Capacity.h"
+#include "llvm/Support/Casting.h"
+#include "llvm/Support/Compiler.h"
+#include "llvm/Support/ErrorHandling.h"
#include "llvm/Support/MathExtras.h"
#include "llvm/Support/raw_ostream.h"
+#include <algorithm>
+#include <cassert>
+#include <cstddef>
+#include <cstdint>
+#include <cstdlib>
#include <map>
+#include <memory>
+#include <string>
+#include <tuple>
+#include <utility>
using namespace clang;
return *Comment;
}
-namespace {
/// If we have a 'templated' declaration for a template, adjust 'D' to
/// refer to the actual template.
/// If we have an implicit instantiation, adjust 'D' to refer to template.
-const Decl *adjustDeclToTemplate(const Decl *D) {
+static const Decl *adjustDeclToTemplate(const Decl *D) {
if (const FunctionDecl *FD = dyn_cast<FunctionDecl>(D)) {
// Is this function declaration part of a function template?
if (const FunctionTemplateDecl *FTD = FD->getDescribedFunctionTemplate())
// FIXME: Adjust alias templates?
return D;
}
-} // anonymous namespace
const RawComment *ASTContext::getRawCommentForAnyRedecl(
const Decl *D,
Builtin::Context &builtins)
: FunctionProtoTypes(this_()), TemplateSpecializationTypes(this_()),
DependentTemplateSpecializationTypes(this_()),
- SubstTemplateTemplateParmPacks(this_()),
- GlobalNestedNameSpecifier(nullptr), Int128Decl(nullptr),
- UInt128Decl(nullptr), BuiltinVaListDecl(nullptr),
- BuiltinMSVaListDecl(nullptr), ObjCIdDecl(nullptr), ObjCSelDecl(nullptr),
- ObjCClassDecl(nullptr), ObjCProtocolClassDecl(nullptr), BOOLDecl(nullptr),
- CFConstantStringTagDecl(nullptr), CFConstantStringTypeDecl(nullptr),
- ObjCInstanceTypeDecl(nullptr), FILEDecl(nullptr), jmp_bufDecl(nullptr),
- sigjmp_bufDecl(nullptr), ucontext_tDecl(nullptr),
- BlockDescriptorType(nullptr), BlockDescriptorExtendedType(nullptr),
- cudaConfigureCallDecl(nullptr), FirstLocalImport(), LastLocalImport(),
- ExternCContext(nullptr), MakeIntegerSeqDecl(nullptr),
- TypePackElementDecl(nullptr), SourceMgr(SM), LangOpts(LOpts),
+ SubstTemplateTemplateParmPacks(this_()), SourceMgr(SM), LangOpts(LOpts),
SanitizerBL(new SanitizerBlacklist(LangOpts.SanitizerBlacklistFiles, SM)),
XRayFilter(new XRayFunctionFilter(LangOpts.XRayAlwaysInstrumentFiles,
LangOpts.XRayNeverInstrumentFiles, SM)),
- AddrSpaceMap(nullptr), Target(nullptr), AuxTarget(nullptr),
PrintingPolicy(LOpts), Idents(idents), Selectors(sels),
- BuiltinInfo(builtins), DeclarationNames(*this), ExternalSource(nullptr),
- Listener(nullptr), Comments(SM), CommentsLoaded(false),
+ BuiltinInfo(builtins), DeclarationNames(*this), Comments(SM),
CommentCommandTraits(BumpAlloc, LOpts.CommentOpts), LastSDM(nullptr, 0) {
TUDecl = TranslationUnitDecl::Create(*this);
}
}
/// \brief Erase the attributes corresponding to the given declaration.
-void ASTContext::eraseDeclAttrs(const Decl *D) {
+void ASTContext::eraseDeclAttrs(const Decl *D) {
llvm::DenseMap<const Decl*, AttrVec*>::iterator Pos = DeclAttrs.find(D);
if (Pos != DeclAttrs.end()) {
Pos->second->~AttrVec();
// else about the declaration and its type.
if (UseAlignAttrOnly) {
// do nothing
-
} else if (const ValueDecl *VD = dyn_cast<ValueDecl>(D)) {
QualType T = VD->getType();
if (const ReferenceType *RT = T->getAs<ReferenceType>()) {
Width = 0;
Align = 8;
break;
-
case BuiltinType::Bool:
Width = Target->getBoolWidth();
Align = Target->getBoolAlign();
Width = Target->getPointerWidth(0);
Align = Target->getPointerAlign(0);
break;
- case Type::BlockPointer: {
+ case Type::BlockPointer:
AS = getTargetAddressSpace(cast<BlockPointerType>(T)->getPointeeType());
Width = Target->getPointerWidth(AS);
Align = Target->getPointerAlign(AS);
break;
- }
case Type::LValueReference:
- case Type::RValueReference: {
+ case Type::RValueReference:
// alignof and sizeof should never enter this code path here, so we go
// the pointer route.
AS = getTargetAddressSpace(cast<ReferenceType>(T)->getPointeeType());
Width = Target->getPointerWidth(AS);
Align = Target->getPointerAlign(AS);
break;
- }
- case Type::Pointer: {
+ case Type::Pointer:
AS = getTargetAddressSpace(cast<PointerType>(T)->getPointeeType());
Width = Target->getPointerWidth(AS);
Align = Target->getPointerAlign(AS);
break;
- }
case Type::MemberPointer: {
const MemberPointerType *MPT = cast<MemberPointerType>(T);
std::tie(Width, Align) = ABI->getMemberPointerWidthAndAlign(MPT);
}
break;
- case Type::Pipe: {
+ case Type::Pipe:
Width = Target->getPointerWidth(getTargetAddressSpace(LangAS::opencl_global));
Align = Target->getPointerAlign(getTargetAddressSpace(LangAS::opencl_global));
- }
-
+ break;
}
assert(llvm::isPowerOf2_32(Align) && "Alignment must be power of 2");
/// super class and then collects all ivars, including those synthesized for
/// current class. This routine is used for implementation of current class
/// when all ivars, declared and synthesized are known.
-///
void ASTContext::DeepCollectObjCIvars(const ObjCInterfaceDecl *OI,
bool leafClass,
SmallVectorImpl<const ObjCIvarDecl*> &Ivars) const {
return false;
}
-/// \brief Get the implementation of ObjCInterfaceDecl,or NULL if none exists.
+/// \brief Get the implementation of ObjCInterfaceDecl, or nullptr if none
+/// exists.
ObjCImplementationDecl *ASTContext::getObjCImplementation(ObjCInterfaceDecl *D) {
llvm::DenseMap<ObjCContainerDecl*, ObjCImplDecl*>::iterator
I = ObjCImpls.find(D);
return cast<ObjCImplementationDecl>(I->second);
return nullptr;
}
-/// \brief Get the implementation of ObjCCategoryDecl, or NULL if none exists.
+
+/// \brief Get the implementation of ObjCCategoryDecl, or nullptr if none
+/// exists.
ObjCCategoryImplDecl *ASTContext::getObjCImplementation(ObjCCategoryDecl *D) {
llvm::DenseMap<ObjCContainerDecl*, ObjCImplDecl*>::iterator
I = ObjCImpls.find(D);
assert(IFaceD && ImplD && "Passed null params");
ObjCImpls[IFaceD] = ImplD;
}
+
/// \brief Set the implementation of ObjCCategoryDecl.
void ASTContext::setObjCImplementation(ObjCCategoryDecl *CatD,
ObjCCategoryImplDecl *ImplD) {
return nullptr;
}
-/// \brief Get the copy initialization expression of VarDecl,or NULL if
+/// \brief Get the copy initialization expression of VarDecl, or nullptr if
/// none exists.
Expr *ASTContext::getBlockVarCopyInits(const VarDecl*VD) {
assert(VD && "Passed null params");
}
/// getFunctionNoProtoType - Return a K&R style C function type like 'int()'.
-///
QualType
ASTContext::getFunctionNoProtoType(QualType ResultTy,
const FunctionType::ExtInfo &Info) const {
llvm::FoldingSetNodeID ID;
PipeType::Profile(ID, T, ReadOnly);
- void *InsertPos = 0;
+ void *InsertPos = nullptr;
if (PipeType *PT = PipeTypes.FindNodeOrInsertPos(ID, InsertPos))
return QualType(PT, 0);
QualType ASTContext::getObjCObjectType(QualType BaseType,
ObjCProtocolDecl * const *Protocols,
unsigned NumProtocols) const {
- return getObjCObjectType(BaseType, { },
+ return getObjCObjectType(BaseType, {},
llvm::makeArrayRef(Protocols, NumProtocols),
/*isKindOf=*/false);
}
// FIXME: Check for protocols to which the class type is already
// known to conform.
- return getObjCObjectType(type, { }, protocols, false);
+ return getObjCObjectType(type, {}, protocols, false);
}
// id<protocol-list>
if (type->isObjCIdType()) {
const ObjCObjectPointerType *objPtr = type->castAs<ObjCObjectPointerType>();
- type = getObjCObjectType(ObjCBuiltinIdTy, { }, protocols,
+ type = getObjCObjectType(ObjCBuiltinIdTy, {}, protocols,
objPtr->isKindOfType());
return getObjCObjectPointerType(type);
}
// Class<protocol-list>
if (type->isObjCClassType()) {
const ObjCObjectPointerType *objPtr = type->castAs<ObjCObjectPointerType>();
- type = getObjCObjectType(ObjCBuiltinClassTy, { }, protocols,
+ type = getObjCObjectType(ObjCBuiltinClassTy, {}, protocols,
objPtr->isKindOfType());
return getObjCObjectPointerType(type);
}
/// getTagDeclType - Return the unique reference to the type for the
/// specified TagDecl (struct/union/class/enum) decl.
QualType ASTContext::getTagDeclType(const TagDecl *Decl) const {
- assert (Decl);
+ assert(Decl);
// FIXME: What is the design on getTagDeclType when it requires casting
// away const? mutable?
return getTypeDeclType(const_cast<TagDecl*>(Decl));
bool ASTContext::getByrefLifetime(QualType Ty,
Qualifiers::ObjCLifetime &LifeTime,
bool &HasByrefExtendedLayout) const {
-
if (!getLangOpts().ObjC1 ||
getLangOpts().getGC() != LangOptions::NonGC)
return false;
CharUnits sz = getObjCEncodingTypeSize(PType);
if (sz.isZero())
continue;
- assert (sz.isPositive() && "BlockExpr - Incomplete param type");
+ assert(sz.isPositive() && "BlockExpr - Incomplete param type");
ParmOffset += sz;
}
// Size of the argument frame
if (sz.isZero())
continue;
- assert (sz.isPositive() &&
- "getObjCEncodingForMethodDecl - Incomplete param type");
+ assert(sz.isPositive() &&
+ "getObjCEncodingForMethodDecl - Incomplete param type");
ParmOffset += sz;
}
S += charUnitsToString(ParmOffset);
/// Another legacy compatibility encoding: 32-bit longs are encoded as
/// 'l' or 'L' , but not always. For typedefs, we need to use
/// 'i' or 'I' instead if encoding a struct field, or a pointer!
-///
void ASTContext::getLegacyIntegralTypeEncoding (QualType &PointeeTy) const {
if (isa<TypedefType>(PointeeTy.getTypePtr())) {
if (const BuiltinType *BT = PointeeTy->getAs<BuiltinType>()) {
case Type::Vector:
case Type::ExtVector:
// Until we have a coherent encoding of these three types, issue warning.
- { if (NotEncodedT)
- *NotEncodedT = T;
- return;
- }
+ if (NotEncodedT)
+ *NotEncodedT = T;
+ return;
// We could see an undeduced auto type here during error recovery.
// Just ignore it.
TypedefDecl *ASTContext::getObjCIdDecl() const {
if (!ObjCIdDecl) {
- QualType T = getObjCObjectType(ObjCBuiltinIdTy, { }, { });
+ QualType T = getObjCObjectType(ObjCBuiltinIdTy, {}, {});
T = getObjCObjectPointerType(T);
ObjCIdDecl = buildImplicitTypedef(T, "id");
}
TypedefDecl *ASTContext::getObjCClassDecl() const {
if (!ObjCClassDecl) {
- QualType T = getObjCObjectType(ObjCBuiltinClassTy, { }, { });
+ QualType T = getObjCObjectType(ObjCBuiltinClassTy, {}, {});
T = getObjCObjectPointerType(T);
ObjCClassDecl = buildImplicitTypedef(T, "Class");
}
QualType rhs) {
const ObjCObjectPointerType *lhsQID = lhs->getAs<ObjCObjectPointerType>();
const ObjCObjectPointerType *rhsOPT = rhs->getAs<ObjCObjectPointerType>();
- assert ((lhsQID && rhsOPT) && "ObjCQualifiedClassTypesAreCompatible");
+ assert((lhsQID && rhsOPT) && "ObjCQualifiedClassTypesAreCompatible");
for (auto *lhsProto : lhsQID->quals()) {
bool match = false;
/// canAssignObjCInterfaces - Return true if the two interface types are
/// compatible for assignment from RHS to LHS. This handles validation of any
/// protocol qualifiers on the LHS or RHS.
-///
bool ASTContext::canAssignObjCInterfaces(const ObjCObjectPointerType *LHSOPT,
const ObjCObjectPointerType *RHSOPT) {
const ObjCObjectType* LHS = LHSOPT->getObjectType();
static int compareObjCProtocolsByName(ObjCProtocolDecl * const *lhs,
ObjCProtocolDecl * const *rhs) {
return (*lhs)->getName().compare((*rhs)->getName());
-
}
/// getIntersectionOfProtocols - This routine finds the intersection of set
} else if (LHS->isSpecialized() != RHS->isSpecialized()) {
// If only one has type arguments, the result will not have type
// arguments.
- LHSTypeArgs = { };
+ LHSTypeArgs = {};
anyChanges = true;
}
} else if (LHS->isSpecialized() != RHS->isSpecialized()) {
// If only one has type arguments, the result will not have type
// arguments.
- RHSTypeArgs = { };
+ RHSTypeArgs = {};
anyChanges = true;
}
return QualType();
}
- case Type::ObjCObjectPointer: {
+ case Type::ObjCObjectPointer:
if (OfBlockPointer) {
if (canAssignObjCInterfacesInBlockPointer(
LHS->getAs<ObjCObjectPointerType>(),
return LHS;
return QualType();
- }
case Type::Pipe:
- {
assert(LHS != RHS &&
"Equivalent pipe types should have already been handled!");
return QualType();
}
- }
llvm_unreachable("Invalid Type::Class!");
}
}
}
-ASTMutationListener::~ASTMutationListener() { }
+ASTMutationListener::~ASTMutationListener() = default;
void ASTMutationListener::DeducedReturnType(const FunctionDecl *FD,
QualType ReturnType) {}
assert(HowLong <= 2 && "Can't have LLLL modifier");
++HowLong;
break;
- case 'N': {
+ case 'N':
// 'N' behaves like 'L' for all non LP64 targets and 'int' otherwise.
assert(!IsSpecialLong && "Can't use two 'N' or 'W' modifiers!");
assert(HowLong == 0 && "Can't use both 'L' and 'N' modifiers!");
if (Context.getTargetInfo().getLongWidth() == 32)
++HowLong;
break;
- }
case 'W':
// This modifier represents int64 type.
assert(!IsSpecialLong && "Can't use two 'N' or 'W' modifiers!");
Type = Context.getComplexType(ElementType);
break;
}
- case 'Y' : {
+ case 'Y':
Type = Context.getPointerDiffType();
break;
- }
case 'P':
Type = Context.getFILEType();
if (Type.isNull()) {
llvm_unreachable("Unsupported ABI");
}
-CXXABI::~CXXABI() {}
+CXXABI::~CXXABI() = default;
size_t ASTContext::getSideTableAllocatedMemory() const {
return ASTRecordLayouts.getMemorySize() +
return (Size != Align || toBits(sizeChars) > MaxInlineWidthInBits);
}
-namespace {
-
-ast_type_traits::DynTypedNode getSingleDynTypedNodeFromParentMap(
+static ast_type_traits::DynTypedNode getSingleDynTypedNodeFromParentMap(
ASTContext::ParentMapPointers::mapped_type U) {
if (const auto *D = U.dyn_cast<const Decl *>())
return ast_type_traits::DynTypedNode::create(*D);
return *U.get<ast_type_traits::DynTypedNode *>();
}
+namespace {
+
/// Template specializations to abstract away from pointers and TypeLocs.
/// @{
template <typename T>
}
private:
- typedef RecursiveASTVisitor<ParentMapASTVisitor> VisitorBase;
+ friend class RecursiveASTVisitor<ParentMapASTVisitor>;
+
+ using VisitorBase = RecursiveASTVisitor<ParentMapASTVisitor>;
ParentMapASTVisitor(ASTContext::ParentMapPointers *Parents,
ASTContext::ParentMapOtherNodes *OtherParents)
bool shouldVisitTemplateInstantiations() const {
return true;
}
+
bool shouldVisitImplicitCode() const {
return true;
}
ASTContext::ParentMapPointers *Parents;
ASTContext::ParentMapOtherNodes *OtherParents;
llvm::SmallVector<ast_type_traits::DynTypedNode, 16> ParentStack;
-
- friend class RecursiveASTVisitor<ParentMapASTVisitor>;
};
-} // anonymous namespace
+} // namespace
template <typename NodeTy, typename MapTy>
static ASTContext::DynTypedNodeList getDynNodeFromMap(const NodeTy &Node,
if (!hasSameType(DeclVar->getType(), ImplVar->getType()))
return false;
}
+
return (MethodDecl->isVariadic() == MethodImpl->isVariadic());
-
}
uint64_t ASTContext::getTargetNullPointerValue(QualType QT) const {