r310436 - [AST] Move visibility computations into a class; NFC
George Burgess IV via cfe-commits
cfe-commits at lists.llvm.org
Thu Aug 10 16:10:03 PDT 2017
Okay, apparently release_capability doesn't work how I assumed, so it
looks like this may be a bug in r310403. Pinged that thread.
On Thu, Aug 10, 2017 at 3:24 PM, George Burgess IV
<george.burgess.iv at gmail.com> wrote:
> Following up, http://green.lab.llvm.org/green/job/clang-stage2-cmake-RgSan_check/4070/console
> no longer shows ubsan failures.
>
> Looks like the attempt to fix Driver/openmp-offload.c is in r310580
> (the linked build was r310538).
>
> The libc++ test failures all seem to be a result of -Werror clang
> emitting warnings as a result of r310403, which gave us more
> diagnostics about thread safety annotations. Glancing at it, seems
> legit. Working on a fix now.
>
> On Wed, Aug 9, 2017 at 2:22 PM, George Burgess IV
> <george.burgess.iv at gmail.com> wrote:
>> Sorry about that!
>>
>> Attempted fix is r310523. I'll keep an eye on the bot to make sure it
>> turns green.
>>
>> On Wed, Aug 9, 2017 at 1:23 PM, Juergen Ributzka <juergen at ributzka.de> wrote:
>>> This seems to cause UBSAN issues:
>>>
>>> runtime error: load of value 4294967295, which is not a valid value for type
>>> 'clang::LVComputationKind'
>>>
>>> See ASAN+UBSAN bot on Green Dragon:
>>> http://lab.llvm.org:8080/green/job/clang-stage2-cmake-RgSan_check/4065/console
>>>
>>> On Tue, Aug 8, 2017 at 9:02 PM, George Burgess IV via cfe-commits
>>> <cfe-commits at lists.llvm.org> wrote:
>>>>
>>>> Author: gbiv
>>>> Date: Tue Aug 8 21:02:49 2017
>>>> New Revision: 310436
>>>>
>>>> URL: http://llvm.org/viewvc/llvm-project?rev=310436&view=rev
>>>> Log:
>>>> [AST] Move visibility computations into a class; NFC
>>>>
>>>> This is patch 1 in a 2 patch series that aims to fix PR29160. Its goal
>>>> is to cache decl visibility/linkage for the duration of each
>>>> visibility+linkage query.
>>>>
>>>> The simplest way I can see to do this is to put the visibility
>>>> calculation code that needs to (transitively) access this cache into a
>>>> class, which is what this patch does. Actual caching will come in patch
>>>> 2. (Another way would be to keep the cache in ASTContext + manually
>>>> invalidate it or something, but that felt way too subtle to me.)
>>>>
>>>> Caching visibility results across multiple queries seems a bit tricky,
>>>> since the user can add visibility attributes ~whenever they want, and
>>>> these attributes can apparently have far-reaching effects (e.g. class
>>>> visibility extends to its members, ...). Because a cache that's dropped
>>>> at the end of each top-level query seems to work nearly as well and
>>>> doesn't require any eviction logic, I opted for that design.
>>>>
>>>> Added:
>>>> cfe/trunk/lib/AST/Linkage.h
>>>> Modified:
>>>> cfe/trunk/lib/AST/Decl.cpp
>>>> cfe/trunk/lib/AST/Type.cpp
>>>>
>>>> Modified: cfe/trunk/lib/AST/Decl.cpp
>>>> URL:
>>>> http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/Decl.cpp?rev=310436&r1=310435&r2=310436&view=diff
>>>>
>>>> ==============================================================================
>>>> --- cfe/trunk/lib/AST/Decl.cpp (original)
>>>> +++ cfe/trunk/lib/AST/Decl.cpp Tue Aug 8 21:02:49 2017
>>>> @@ -12,6 +12,7 @@
>>>>
>>>> //===----------------------------------------------------------------------===//
>>>>
>>>> #include "clang/AST/Decl.h"
>>>> +#include "Linkage.h"
>>>> #include "clang/AST/ASTContext.h"
>>>> #include "clang/AST/ASTLambda.h"
>>>> #include "clang/AST/ASTMutationListener.h"
>>>> @@ -99,38 +100,6 @@ TranslationUnitDecl::TranslationUnitDecl
>>>> // and 'matcher' is a type only matters when looking for attributes
>>>> // and settings from the immediate context.
>>>>
>>>> -const static unsigned IgnoreExplicitVisibilityBit = 2;
>>>> -const static unsigned IgnoreAllVisibilityBit = 4;
>>>> -
>>>> -/// Kinds of LV computation. The linkage side of the computation is
>>>> -/// always the same, but different things can change how visibility is
>>>> -/// computed.
>>>> -enum LVComputationKind {
>>>> - /// Do an LV computation for, ultimately, a type.
>>>> - /// Visibility may be restricted by type visibility settings and
>>>> - /// the visibility of template arguments.
>>>> - LVForType = NamedDecl::VisibilityForType,
>>>> -
>>>> - /// Do an LV computation for, ultimately, a non-type declaration.
>>>> - /// Visibility may be restricted by value visibility settings and
>>>> - /// the visibility of template arguments.
>>>> - LVForValue = NamedDecl::VisibilityForValue,
>>>> -
>>>> - /// Do an LV computation for, ultimately, a type that already has
>>>> - /// some sort of explicit visibility. Visibility may only be
>>>> - /// restricted by the visibility of template arguments.
>>>> - LVForExplicitType = (LVForType | IgnoreExplicitVisibilityBit),
>>>> -
>>>> - /// Do an LV computation for, ultimately, a non-type declaration
>>>> - /// that already has some sort of explicit visibility. Visibility
>>>> - /// may only be restricted by the visibility of template arguments.
>>>> - LVForExplicitValue = (LVForValue | IgnoreExplicitVisibilityBit),
>>>> -
>>>> - /// Do an LV computation when we only care about the linkage.
>>>> - LVForLinkageOnly =
>>>> - LVForValue | IgnoreExplicitVisibilityBit | IgnoreAllVisibilityBit
>>>> -};
>>>> -
>>>> /// Does this computation kind permit us to consider additional
>>>> /// visibility settings from attributes and the like?
>>>> static bool hasExplicitVisibilityAlready(LVComputationKind computation) {
>>>> @@ -219,8 +188,8 @@ static Optional<Visibility> getVisibilit
>>>> return None;
>>>> }
>>>>
>>>> -static LinkageInfo
>>>> -getLVForType(const Type &T, LVComputationKind computation) {
>>>> +LinkageInfo LinkageComputer::getLVForType(const Type &T,
>>>> + LVComputationKind computation)
>>>> {
>>>> if (computation == LVForLinkageOnly)
>>>> return LinkageInfo(T.getLinkage(), DefaultVisibility, true);
>>>> return T.getLinkageAndVisibility();
>>>> @@ -229,9 +198,8 @@ getLVForType(const Type &T, LVComputatio
>>>> /// \brief Get the most restrictive linkage for the types in the given
>>>> /// template parameter list. For visibility purposes, template
>>>> /// parameters are part of the signature of a template.
>>>> -static LinkageInfo
>>>> -getLVForTemplateParameterList(const TemplateParameterList *Params,
>>>> - LVComputationKind computation) {
>>>> +LinkageInfo LinkageComputer::getLVForTemplateParameterList(
>>>> + const TemplateParameterList *Params, LVComputationKind computation) {
>>>> LinkageInfo LV;
>>>> for (const NamedDecl *P : *Params) {
>>>> // Template type parameters are the most common and never
>>>> @@ -283,10 +251,6 @@ getLVForTemplateParameterList(const Temp
>>>> return LV;
>>>> }
>>>>
>>>> -/// getLVForDecl - Get the linkage and visibility for the given
>>>> declaration.
>>>> -static LinkageInfo getLVForDecl(const NamedDecl *D,
>>>> - LVComputationKind computation);
>>>> -
>>>> static const Decl *getOutermostFuncOrBlockContext(const Decl *D) {
>>>> const Decl *Ret = nullptr;
>>>> const DeclContext *DC = D->getDeclContext();
>>>> @@ -303,8 +267,9 @@ static const Decl *getOutermostFuncOrBlo
>>>> ///
>>>> /// Note that we don't take an LVComputationKind because we always
>>>> /// want to honor the visibility of template arguments in the same way.
>>>> -static LinkageInfo
>>>> getLVForTemplateArgumentList(ArrayRef<TemplateArgument> Args,
>>>> - LVComputationKind
>>>> computation) {
>>>> +LinkageInfo
>>>> +LinkageComputer::getLVForTemplateArgumentList(ArrayRef<TemplateArgument>
>>>> Args,
>>>> + LVComputationKind
>>>> computation) {
>>>> LinkageInfo LV;
>>>>
>>>> for (const TemplateArgument &Arg : Args) {
>>>> @@ -346,9 +311,9 @@ static LinkageInfo getLVForTemplateArgum
>>>> return LV;
>>>> }
>>>>
>>>> -static LinkageInfo
>>>> -getLVForTemplateArgumentList(const TemplateArgumentList &TArgs,
>>>> - LVComputationKind computation) {
>>>> +LinkageInfo
>>>> +LinkageComputer::getLVForTemplateArgumentList(const TemplateArgumentList
>>>> &TArgs,
>>>> + LVComputationKind
>>>> computation) {
>>>> return getLVForTemplateArgumentList(TArgs.asArray(), computation);
>>>> }
>>>>
>>>> @@ -371,10 +336,10 @@ static bool shouldConsiderTemplateVisibi
>>>> /// LVForValue.
>>>> ///
>>>> /// \param[out] LV the computation to use for the parent
>>>> -static void
>>>> -mergeTemplateLV(LinkageInfo &LV, const FunctionDecl *fn,
>>>> - const FunctionTemplateSpecializationInfo *specInfo,
>>>> - LVComputationKind computation) {
>>>> +void LinkageComputer::mergeTemplateLV(
>>>> + LinkageInfo &LV, const FunctionDecl *fn,
>>>> + const FunctionTemplateSpecializationInfo *specInfo,
>>>> + LVComputationKind computation) {
>>>> bool considerVisibility =
>>>> shouldConsiderTemplateVisibility(fn, specInfo);
>>>>
>>>> @@ -449,9 +414,9 @@ static bool shouldConsiderTemplateVisibi
>>>>
>>>> /// Merge in template-related linkage and visibility for the given
>>>> /// class template specialization.
>>>> -static void mergeTemplateLV(LinkageInfo &LV,
>>>> - const ClassTemplateSpecializationDecl *spec,
>>>> - LVComputationKind computation) {
>>>> +void LinkageComputer::mergeTemplateLV(
>>>> + LinkageInfo &LV, const ClassTemplateSpecializationDecl *spec,
>>>> + LVComputationKind computation) {
>>>> bool considerVisibility = shouldConsiderTemplateVisibility(spec,
>>>> computation);
>>>>
>>>> // Merge information from the template parameters, but ignore
>>>> @@ -501,9 +466,9 @@ static bool shouldConsiderTemplateVisibi
>>>> /// Merge in template-related linkage and visibility for the given
>>>> /// variable template specialization. As usual, follow class template
>>>> /// specialization logic up to initialization.
>>>> -static void mergeTemplateLV(LinkageInfo &LV,
>>>> - const VarTemplateSpecializationDecl *spec,
>>>> - LVComputationKind computation) {
>>>> +void LinkageComputer::mergeTemplateLV(LinkageInfo &LV,
>>>> + const VarTemplateSpecializationDecl
>>>> *spec,
>>>> + LVComputationKind computation) {
>>>> bool considerVisibility = shouldConsiderTemplateVisibility(spec,
>>>> computation);
>>>>
>>>> // Merge information from the template parameters, but ignore
>>>> @@ -603,8 +568,9 @@ static LinkageInfo getExternalLinkageFor
>>>> return LinkageInfo::external();
>>>> }
>>>>
>>>> -static LinkageInfo getLVForNamespaceScopeDecl(const NamedDecl *D,
>>>> - LVComputationKind
>>>> computation) {
>>>> +LinkageInfo
>>>> +LinkageComputer::getLVForNamespaceScopeDecl(const NamedDecl *D,
>>>> + LVComputationKind
>>>> computation) {
>>>> assert(D->getDeclContext()->getRedeclContext()->isFileContext() &&
>>>> "Not a name having namespace scope");
>>>> ASTContext &Context = D->getASTContext();
>>>> @@ -883,8 +849,9 @@ static LinkageInfo getLVForNamespaceScop
>>>> return LV;
>>>> }
>>>>
>>>> -static LinkageInfo getLVForClassMember(const NamedDecl *D,
>>>> - LVComputationKind computation) {
>>>> +LinkageInfo
>>>> +LinkageComputer::getLVForClassMember(const NamedDecl *D,
>>>> + LVComputationKind computation) {
>>>> // Only certain class members have linkage. Note that fields don't
>>>> // really have linkage, but it's convenient to say they do for the
>>>> // purposes of calculating linkage of pointer-to-data-member
>>>> @@ -1041,15 +1008,13 @@ static LinkageInfo getLVForClassMember(c
>>>>
>>>> void NamedDecl::anchor() { }
>>>>
>>>> -static LinkageInfo computeLVForDecl(const NamedDecl *D,
>>>> - LVComputationKind computation);
>>>> -
>>>> bool NamedDecl::isLinkageValid() const {
>>>> if (!hasCachedLinkage())
>>>> return true;
>>>>
>>>> - return computeLVForDecl(this, LVForLinkageOnly).getLinkage() ==
>>>> - getCachedLinkage();
>>>> + Linkage L =
>>>> + LinkageComputer{}.computeLVForDecl(this,
>>>> LVForLinkageOnly).getLinkage();
>>>> + return L == getCachedLinkage();
>>>> }
>>>>
>>>> ObjCStringFormatFamily NamedDecl::getObjCFStringFormattingFamily() const
>>>> {
>>>> @@ -1068,13 +1033,11 @@ ObjCStringFormatFamily NamedDecl::getObj
>>>> Linkage NamedDecl::getLinkageInternal() const {
>>>> // We don't care about visibility here, so ask for the cheapest
>>>> // possible visibility analysis.
>>>> - return getLVForDecl(this, LVForLinkageOnly).getLinkage();
>>>> + return LinkageComputer{}.getLVForDecl(this,
>>>> LVForLinkageOnly).getLinkage();
>>>> }
>>>>
>>>> LinkageInfo NamedDecl::getLinkageAndVisibility() const {
>>>> - LVComputationKind computation =
>>>> - (usesTypeVisibility(this) ? LVForType : LVForValue);
>>>> - return getLVForDecl(this, computation);
>>>> + return LinkageComputer{}.getDeclLinkageAndVisibility(this);
>>>> }
>>>>
>>>> static Optional<Visibility>
>>>> @@ -1152,8 +1115,9 @@ NamedDecl::getExplicitVisibility(Explici
>>>> return getExplicitVisibilityAux(this, kind, false);
>>>> }
>>>>
>>>> -static LinkageInfo getLVForClosure(const DeclContext *DC, Decl
>>>> *ContextDecl,
>>>> - LVComputationKind computation) {
>>>> +LinkageInfo LinkageComputer::getLVForClosure(const DeclContext *DC,
>>>> + Decl *ContextDecl,
>>>> + LVComputationKind
>>>> computation) {
>>>> // This lambda has its linkage/visibility determined by its owner.
>>>> if (ContextDecl) {
>>>> if (isa<ParmVarDecl>(ContextDecl))
>>>> @@ -1170,8 +1134,8 @@ static LinkageInfo getLVForClosure(const
>>>> return LinkageInfo::external();
>>>> }
>>>>
>>>> -static LinkageInfo getLVForLocalDecl(const NamedDecl *D,
>>>> - LVComputationKind computation) {
>>>> +LinkageInfo LinkageComputer::getLVForLocalDecl(const NamedDecl *D,
>>>> + LVComputationKind
>>>> computation) {
>>>> if (const auto *Function = dyn_cast<FunctionDecl>(D)) {
>>>> if (Function->isInAnonymousNamespace() &&
>>>> !Function->isInExternCContext())
>>>> @@ -1264,8 +1228,8 @@ getOutermostEnclosingLambda(const CXXRec
>>>> return Ret;
>>>> }
>>>>
>>>> -static LinkageInfo computeLVForDecl(const NamedDecl *D,
>>>> - LVComputationKind computation) {
>>>> +LinkageInfo LinkageComputer::computeLVForDecl(const NamedDecl *D,
>>>> + LVComputationKind
>>>> computation) {
>>>> // Internal_linkage attribute overrides other considerations.
>>>> if (D->hasAttr<InternalLinkageAttr>())
>>>> return getInternalLinkageFor(D);
>>>> @@ -1384,56 +1348,51 @@ static LinkageInfo computeLVForDecl(cons
>>>> return LinkageInfo::none();
>>>> }
>>>>
>>>> -namespace clang {
>>>> -class LinkageComputer {
>>>> -public:
>>>> - static LinkageInfo getLVForDecl(const NamedDecl *D,
>>>> - LVComputationKind computation) {
>>>> - // Internal_linkage attribute overrides other considerations.
>>>> - if (D->hasAttr<InternalLinkageAttr>())
>>>> - return getInternalLinkageFor(D);
>>>> -
>>>> - if (computation == LVForLinkageOnly && D->hasCachedLinkage())
>>>> - return LinkageInfo(D->getCachedLinkage(), DefaultVisibility,
>>>> false);
>>>> -
>>>> - LinkageInfo LV = computeLVForDecl(D, computation);
>>>> - if (D->hasCachedLinkage())
>>>> - assert(D->getCachedLinkage() == LV.getLinkage());
>>>> +/// getLVForDecl - Get the linkage and visibility for the given
>>>> declaration.
>>>> +LinkageInfo LinkageComputer::getLVForDecl(const NamedDecl *D,
>>>> + LVComputationKind computation)
>>>> {
>>>> + // Internal_linkage attribute overrides other considerations.
>>>> + if (D->hasAttr<InternalLinkageAttr>())
>>>> + return getInternalLinkageFor(D);
>>>> +
>>>> + if (computation == LVForLinkageOnly && D->hasCachedLinkage())
>>>> + return LinkageInfo(D->getCachedLinkage(), DefaultVisibility, false);
>>>>
>>>> - D->setCachedLinkage(LV.getLinkage());
>>>> + LinkageInfo LV = computeLVForDecl(D, computation);
>>>> + if (D->hasCachedLinkage())
>>>> + assert(D->getCachedLinkage() == LV.getLinkage());
>>>> +
>>>> + D->setCachedLinkage(LV.getLinkage());
>>>>
>>>> #ifndef NDEBUG
>>>> - // In C (because of gnu inline) and in c++ with microsoft extensions
>>>> an
>>>> - // static can follow an extern, so we can have two decls with
>>>> different
>>>> - // linkages.
>>>> - const LangOptions &Opts = D->getASTContext().getLangOpts();
>>>> - if (!Opts.CPlusPlus || Opts.MicrosoftExt)
>>>> - return LV;
>>>> + // In C (because of gnu inline) and in c++ with microsoft extensions an
>>>> + // static can follow an extern, so we can have two decls with different
>>>> + // linkages.
>>>> + const LangOptions &Opts = D->getASTContext().getLangOpts();
>>>> + if (!Opts.CPlusPlus || Opts.MicrosoftExt)
>>>> + return LV;
>>>>
>>>> - // We have just computed the linkage for this decl. By induction we
>>>> know
>>>> - // that all other computed linkages match, check that the one we just
>>>> - // computed also does.
>>>> - NamedDecl *Old = nullptr;
>>>> - for (auto I : D->redecls()) {
>>>> - auto *T = cast<NamedDecl>(I);
>>>> - if (T == D)
>>>> - continue;
>>>> - if (!T->isInvalidDecl() && T->hasCachedLinkage()) {
>>>> - Old = T;
>>>> - break;
>>>> - }
>>>> + // We have just computed the linkage for this decl. By induction we
>>>> know
>>>> + // that all other computed linkages match, check that the one we just
>>>> + // computed also does.
>>>> + NamedDecl *Old = nullptr;
>>>> + for (auto I : D->redecls()) {
>>>> + auto *T = cast<NamedDecl>(I);
>>>> + if (T == D)
>>>> + continue;
>>>> + if (!T->isInvalidDecl() && T->hasCachedLinkage()) {
>>>> + Old = T;
>>>> + break;
>>>> }
>>>> - assert(!Old || Old->getCachedLinkage() == D->getCachedLinkage());
>>>> + }
>>>> + assert(!Old || Old->getCachedLinkage() == D->getCachedLinkage());
>>>> #endif
>>>>
>>>> - return LV;
>>>> - }
>>>> -};
>>>> + return LV;
>>>> }
>>>>
>>>> -static LinkageInfo getLVForDecl(const NamedDecl *D,
>>>> - LVComputationKind computation) {
>>>> - return clang::LinkageComputer::getLVForDecl(D, computation);
>>>> +LinkageInfo LinkageComputer::getDeclLinkageAndVisibility(const NamedDecl
>>>> *D) {
>>>> + return getLVForDecl(D, usesTypeVisibility(D) ? LVForType : LVForValue);
>>>> }
>>>>
>>>> void NamedDecl::printName(raw_ostream &os) const {
>>>>
>>>> Added: cfe/trunk/lib/AST/Linkage.h
>>>> URL:
>>>> http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/Linkage.h?rev=310436&view=auto
>>>>
>>>> ==============================================================================
>>>> --- cfe/trunk/lib/AST/Linkage.h (added)
>>>> +++ cfe/trunk/lib/AST/Linkage.h Tue Aug 8 21:02:49 2017
>>>> @@ -0,0 +1,114 @@
>>>> +//===----- Linkage.h - Linkage calculation-related utilities ----*- C++
>>>> -*-===//
>>>> +//
>>>> +// The LLVM Compiler Infrastructure
>>>> +//
>>>> +// This file is distributed under the University of Illinois Open Source
>>>> +// License. See LICENSE.TXT for details.
>>>> +//
>>>>
>>>> +//===----------------------------------------------------------------------===//
>>>> +//
>>>> +// This file provides AST-internal utilities for linkage and visibility
>>>> +// calculation.
>>>> +//
>>>>
>>>> +//===----------------------------------------------------------------------===//
>>>> +
>>>> +#ifndef LLVM_CLANG_LIB_AST_LINKAGE_H
>>>> +#define LLVM_CLANG_LIB_AST_LINKAGE_H
>>>> +
>>>> +#include "clang/AST/Decl.h"
>>>> +#include "clang/AST/DeclCXX.h"
>>>> +#include "clang/AST/Type.h"
>>>> +#include "llvm/ADT/DenseMap.h"
>>>> +
>>>> +namespace clang {
>>>> +enum : unsigned {
>>>> + IgnoreExplicitVisibilityBit = 2,
>>>> + IgnoreAllVisibilityBit = 4
>>>> +};
>>>> +
>>>> +/// Kinds of LV computation. The linkage side of the computation is
>>>> +/// always the same, but different things can change how visibility is
>>>> +/// computed.
>>>> +enum LVComputationKind {
>>>> + /// Do an LV computation for, ultimately, a type.
>>>> + /// Visibility may be restricted by type visibility settings and
>>>> + /// the visibility of template arguments.
>>>> + LVForType = NamedDecl::VisibilityForType,
>>>> +
>>>> + /// Do an LV computation for, ultimately, a non-type declaration.
>>>> + /// Visibility may be restricted by value visibility settings and
>>>> + /// the visibility of template arguments.
>>>> + LVForValue = NamedDecl::VisibilityForValue,
>>>> +
>>>> + /// Do an LV computation for, ultimately, a type that already has
>>>> + /// some sort of explicit visibility. Visibility may only be
>>>> + /// restricted by the visibility of template arguments.
>>>> + LVForExplicitType = (LVForType | IgnoreExplicitVisibilityBit),
>>>> +
>>>> + /// Do an LV computation for, ultimately, a non-type declaration
>>>> + /// that already has some sort of explicit visibility. Visibility
>>>> + /// may only be restricted by the visibility of template arguments.
>>>> + LVForExplicitValue = (LVForValue | IgnoreExplicitVisibilityBit),
>>>> +
>>>> + /// Do an LV computation when we only care about the linkage.
>>>> + LVForLinkageOnly =
>>>> + LVForValue | IgnoreExplicitVisibilityBit | IgnoreAllVisibilityBit
>>>> +};
>>>> +
>>>> +class LinkageComputer {
>>>> + LinkageInfo getLVForTemplateArgumentList(ArrayRef<TemplateArgument>
>>>> Args,
>>>> + LVComputationKind
>>>> computation);
>>>> +
>>>> + LinkageInfo getLVForTemplateArgumentList(const TemplateArgumentList
>>>> &TArgs,
>>>> + LVComputationKind
>>>> computation);
>>>> +
>>>> + void mergeTemplateLV(LinkageInfo &LV, const FunctionDecl *fn,
>>>> + const FunctionTemplateSpecializationInfo
>>>> *specInfo,
>>>> + LVComputationKind computation);
>>>> +
>>>> + void mergeTemplateLV(LinkageInfo &LV,
>>>> + const ClassTemplateSpecializationDecl *spec,
>>>> + LVComputationKind computation);
>>>> +
>>>> + void mergeTemplateLV(LinkageInfo &LV,
>>>> + const VarTemplateSpecializationDecl *spec,
>>>> + LVComputationKind computation);
>>>> +
>>>> + LinkageInfo getLVForNamespaceScopeDecl(const NamedDecl *D,
>>>> + LVComputationKind computation);
>>>> +
>>>> + LinkageInfo getLVForClassMember(const NamedDecl *D,
>>>> + LVComputationKind computation);
>>>> +
>>>> + LinkageInfo getLVForClosure(const DeclContext *DC, Decl *ContextDecl,
>>>> + LVComputationKind computation);
>>>> +
>>>> + LinkageInfo getLVForLocalDecl(const NamedDecl *D,
>>>> + LVComputationKind computation);
>>>> +
>>>> + LinkageInfo getLVForType(const Type &T, LVComputationKind computation);
>>>> +
>>>> + LinkageInfo getLVForTemplateParameterList(const TemplateParameterList
>>>> *Params,
>>>> + LVComputationKind
>>>> computation);
>>>> +
>>>> +public:
>>>> + LinkageInfo computeLVForDecl(const NamedDecl *D,
>>>> + LVComputationKind computation);
>>>> +
>>>> + LinkageInfo getLVForDecl(const NamedDecl *D, LVComputationKind
>>>> computation);
>>>> +
>>>> + LinkageInfo computeTypeLinkageInfo(const Type *T);
>>>> + LinkageInfo computeTypeLinkageInfo(QualType T) {
>>>> + return computeTypeLinkageInfo(T.getTypePtr());
>>>> + }
>>>> +
>>>> + LinkageInfo getDeclLinkageAndVisibility(const NamedDecl *D);
>>>> +
>>>> + LinkageInfo getTypeLinkageAndVisibility(const Type *T);
>>>> + LinkageInfo getTypeLinkageAndVisibility(QualType T) {
>>>> + return getTypeLinkageAndVisibility(T.getTypePtr());
>>>> + }
>>>> +};
>>>> +} // namespace clang
>>>> +
>>>> +#endif
>>>>
>>>> Modified: cfe/trunk/lib/AST/Type.cpp
>>>> URL:
>>>> http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/Type.cpp?rev=310436&r1=310435&r2=310436&view=diff
>>>>
>>>> ==============================================================================
>>>> --- cfe/trunk/lib/AST/Type.cpp (original)
>>>> +++ cfe/trunk/lib/AST/Type.cpp Tue Aug 8 21:02:49 2017
>>>> @@ -12,6 +12,7 @@
>>>>
>>>> //===----------------------------------------------------------------------===//
>>>>
>>>> #include "clang/AST/Type.h"
>>>> +#include "Linkage.h"
>>>> #include "clang/AST/ASTContext.h"
>>>> #include "clang/AST/Attr.h"
>>>> #include "clang/AST/CharUnits.h"
>>>> @@ -3428,9 +3429,7 @@ bool Type::hasUnnamedOrLocalType() const
>>>> return TypeBits.hasLocalOrUnnamedType();
>>>> }
>>>>
>>>> -static LinkageInfo computeLinkageInfo(QualType T);
>>>> -
>>>> -static LinkageInfo computeLinkageInfo(const Type *T) {
>>>> +LinkageInfo LinkageComputer::computeTypeLinkageInfo(const Type *T) {
>>>> switch (T->getTypeClass()) {
>>>> #define TYPE(Class,Base)
>>>> #define NON_CANONICAL_TYPE(Class,Base) case Type::Class:
>>>> @@ -3457,72 +3456,75 @@ static LinkageInfo computeLinkageInfo(co
>>>> return cast<TagType>(T)->getDecl()->getLinkageAndVisibility();
>>>>
>>>> case Type::Complex:
>>>> - return computeLinkageInfo(cast<ComplexType>(T)->getElementType());
>>>> + return
>>>> computeTypeLinkageInfo(cast<ComplexType>(T)->getElementType());
>>>> case Type::Pointer:
>>>> - return computeLinkageInfo(cast<PointerType>(T)->getPointeeType());
>>>> + return
>>>> computeTypeLinkageInfo(cast<PointerType>(T)->getPointeeType());
>>>> case Type::BlockPointer:
>>>> - return
>>>> computeLinkageInfo(cast<BlockPointerType>(T)->getPointeeType());
>>>> + return
>>>> computeTypeLinkageInfo(cast<BlockPointerType>(T)->getPointeeType());
>>>> case Type::LValueReference:
>>>> case Type::RValueReference:
>>>> - return computeLinkageInfo(cast<ReferenceType>(T)->getPointeeType());
>>>> + return
>>>> computeTypeLinkageInfo(cast<ReferenceType>(T)->getPointeeType());
>>>> case Type::MemberPointer: {
>>>> const MemberPointerType *MPT = cast<MemberPointerType>(T);
>>>> - LinkageInfo LV = computeLinkageInfo(MPT->getClass());
>>>> - LV.merge(computeLinkageInfo(MPT->getPointeeType()));
>>>> + LinkageInfo LV = computeTypeLinkageInfo(MPT->getClass());
>>>> + LV.merge(computeTypeLinkageInfo(MPT->getPointeeType()));
>>>> return LV;
>>>> }
>>>> case Type::ConstantArray:
>>>> case Type::IncompleteArray:
>>>> case Type::VariableArray:
>>>> - return computeLinkageInfo(cast<ArrayType>(T)->getElementType());
>>>> + return computeTypeLinkageInfo(cast<ArrayType>(T)->getElementType());
>>>> case Type::Vector:
>>>> case Type::ExtVector:
>>>> - return computeLinkageInfo(cast<VectorType>(T)->getElementType());
>>>> + return computeTypeLinkageInfo(cast<VectorType>(T)->getElementType());
>>>> case Type::FunctionNoProto:
>>>> - return computeLinkageInfo(cast<FunctionType>(T)->getReturnType());
>>>> + return
>>>> computeTypeLinkageInfo(cast<FunctionType>(T)->getReturnType());
>>>> case Type::FunctionProto: {
>>>> const FunctionProtoType *FPT = cast<FunctionProtoType>(T);
>>>> - LinkageInfo LV = computeLinkageInfo(FPT->getReturnType());
>>>> + LinkageInfo LV = computeTypeLinkageInfo(FPT->getReturnType());
>>>> for (const auto &ai : FPT->param_types())
>>>> - LV.merge(computeLinkageInfo(ai));
>>>> + LV.merge(computeTypeLinkageInfo(ai));
>>>> return LV;
>>>> }
>>>> case Type::ObjCInterface:
>>>> return
>>>> cast<ObjCInterfaceType>(T)->getDecl()->getLinkageAndVisibility();
>>>> case Type::ObjCObject:
>>>> - return computeLinkageInfo(cast<ObjCObjectType>(T)->getBaseType());
>>>> + return
>>>> computeTypeLinkageInfo(cast<ObjCObjectType>(T)->getBaseType());
>>>> case Type::ObjCObjectPointer:
>>>> - return
>>>> computeLinkageInfo(cast<ObjCObjectPointerType>(T)->getPointeeType());
>>>> + return computeTypeLinkageInfo(
>>>> + cast<ObjCObjectPointerType>(T)->getPointeeType());
>>>> case Type::Atomic:
>>>> - return computeLinkageInfo(cast<AtomicType>(T)->getValueType());
>>>> + return computeTypeLinkageInfo(cast<AtomicType>(T)->getValueType());
>>>> case Type::Pipe:
>>>> - return computeLinkageInfo(cast<PipeType>(T)->getElementType());
>>>> + return computeTypeLinkageInfo(cast<PipeType>(T)->getElementType());
>>>> }
>>>>
>>>> llvm_unreachable("unhandled type class");
>>>> }
>>>>
>>>> -static LinkageInfo computeLinkageInfo(QualType T) {
>>>> - return computeLinkageInfo(T.getTypePtr());
>>>> -}
>>>> -
>>>> bool Type::isLinkageValid() const {
>>>> if (!TypeBits.isCacheValid())
>>>> return true;
>>>>
>>>> - return computeLinkageInfo(getCanonicalTypeInternal()).getLinkage() ==
>>>> - TypeBits.getLinkage();
>>>> + Linkage L = LinkageComputer{}
>>>> + .computeTypeLinkageInfo(getCanonicalTypeInternal())
>>>> + .getLinkage();
>>>> + return L == TypeBits.getLinkage();
>>>> }
>>>>
>>>> -LinkageInfo Type::getLinkageAndVisibility() const {
>>>> - if (!isCanonicalUnqualified())
>>>> - return computeLinkageInfo(getCanonicalTypeInternal());
>>>> +LinkageInfo LinkageComputer::getTypeLinkageAndVisibility(const Type *T) {
>>>> + if (!T->isCanonicalUnqualified())
>>>> + return computeTypeLinkageInfo(T->getCanonicalTypeInternal());
>>>>
>>>> - LinkageInfo LV = computeLinkageInfo(this);
>>>> - assert(LV.getLinkage() == getLinkage());
>>>> + LinkageInfo LV = computeTypeLinkageInfo(T);
>>>> + assert(LV.getLinkage() == T->getLinkage());
>>>> return LV;
>>>> }
>>>>
>>>> +LinkageInfo Type::getLinkageAndVisibility() const {
>>>> + return LinkageComputer{}.getTypeLinkageAndVisibility(this);
>>>> +}
>>>> +
>>>> Optional<NullabilityKind> Type::getNullability(const ASTContext &context)
>>>> const {
>>>> QualType type(this, 0);
>>>> do {
>>>>
>>>>
>>>> _______________________________________________
>>>> cfe-commits mailing list
>>>> cfe-commits at lists.llvm.org
>>>> http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
>>>
>>>
More information about the cfe-commits
mailing list