Merge llvm, clang, compiler-rt, libc++, libunwind, lld, lldb and openmp
llvmorg-10.0.0-rc4-5-g52c365aa9ca. The actual release should follow Real Soon Now. PR: 244251 MFC after: 6 weeks
This commit is contained in:
commit
cd675bb60e
Notes:
svn2git
2020-12-20 02:59:44 +00:00
svn path=/head/; revision=359082
@ -3955,14 +3955,18 @@ class StmtExpr : public Expr {
|
||||
Stmt *SubStmt;
|
||||
SourceLocation LParenLoc, RParenLoc;
|
||||
public:
|
||||
StmtExpr(CompoundStmt *substmt, QualType T,
|
||||
SourceLocation lp, SourceLocation rp, bool InDependentContext) :
|
||||
// Note: we treat a statement-expression in a dependent context as always
|
||||
// being value- and instantiation-dependent. This matches the behavior of
|
||||
// lambda-expressions and GCC.
|
||||
Expr(StmtExprClass, T, VK_RValue, OK_Ordinary,
|
||||
T->isDependentType(), InDependentContext, InDependentContext, false),
|
||||
SubStmt(substmt), LParenLoc(lp), RParenLoc(rp) {}
|
||||
StmtExpr(CompoundStmt *SubStmt, QualType T, SourceLocation LParenLoc,
|
||||
SourceLocation RParenLoc, unsigned TemplateDepth)
|
||||
: // We treat a statement-expression in a dependent context as
|
||||
// always being value- and instantiation-dependent. This matches the
|
||||
// behavior of lambda-expressions and GCC.
|
||||
Expr(StmtExprClass, T, VK_RValue, OK_Ordinary, T->isDependentType(),
|
||||
TemplateDepth != 0, TemplateDepth != 0, false),
|
||||
SubStmt(SubStmt), LParenLoc(LParenLoc), RParenLoc(RParenLoc) {
|
||||
// FIXME: A templated statement expression should have an associated
|
||||
// DeclContext so that nested declarations always have a dependent context.
|
||||
StmtExprBits.TemplateDepth = TemplateDepth;
|
||||
}
|
||||
|
||||
/// Build an empty statement expression.
|
||||
explicit StmtExpr(EmptyShell Empty) : Expr(StmtExprClass, Empty) { }
|
||||
@ -3979,6 +3983,8 @@ class StmtExpr : public Expr {
|
||||
SourceLocation getRParenLoc() const { return RParenLoc; }
|
||||
void setRParenLoc(SourceLocation L) { RParenLoc = L; }
|
||||
|
||||
unsigned getTemplateDepth() const { return StmtExprBits.TemplateDepth; }
|
||||
|
||||
static bool classof(const Stmt *T) {
|
||||
return T->getStmtClass() == StmtExprClass;
|
||||
}
|
||||
|
@ -588,6 +588,18 @@ class alignas(void *) Stmt {
|
||||
unsigned Kind : 2;
|
||||
};
|
||||
|
||||
class StmtExprBitfields {
|
||||
friend class ASTStmtReader;
|
||||
friend class StmtExpr;
|
||||
|
||||
unsigned : NumExprBits;
|
||||
|
||||
/// The number of levels of template parameters enclosing this statement
|
||||
/// expression. Used to determine if a statement expression remains
|
||||
/// dependent after instantiation.
|
||||
unsigned TemplateDepth;
|
||||
};
|
||||
|
||||
//===--- C++ Expression bitfields classes ---===//
|
||||
|
||||
class CXXOperatorCallExprBitfields {
|
||||
@ -996,6 +1008,9 @@ class alignas(void *) Stmt {
|
||||
PseudoObjectExprBitfields PseudoObjectExprBits;
|
||||
SourceLocExprBitfields SourceLocExprBits;
|
||||
|
||||
// GNU Extensions.
|
||||
StmtExprBitfields StmtExprBits;
|
||||
|
||||
// C++ Expressions
|
||||
CXXOperatorCallExprBitfields CXXOperatorCallExprBits;
|
||||
CXXRewrittenBinaryOperatorBitfields CXXRewrittenBinaryOperatorBits;
|
||||
|
@ -620,6 +620,15 @@ class Sema final {
|
||||
/// function, block, and method scopes that are currently active.
|
||||
SmallVector<sema::FunctionScopeInfo *, 4> FunctionScopes;
|
||||
|
||||
/// The index of the first FunctionScope that corresponds to the current
|
||||
/// context.
|
||||
unsigned FunctionScopesStart = 0;
|
||||
|
||||
ArrayRef<sema::FunctionScopeInfo*> getFunctionScopes() const {
|
||||
return llvm::makeArrayRef(FunctionScopes.begin() + FunctionScopesStart,
|
||||
FunctionScopes.end());
|
||||
}
|
||||
|
||||
/// Stack containing information needed when in C++2a an 'auto' is encountered
|
||||
/// in a function declaration parameter type specifier in order to invent a
|
||||
/// corresponding template parameter in the enclosing abbreviated function
|
||||
@ -627,6 +636,16 @@ class Sema final {
|
||||
/// the FunctionScopes stack.
|
||||
SmallVector<InventedTemplateParameterInfo, 4> InventedParameterInfos;
|
||||
|
||||
/// The index of the first InventedParameterInfo that refers to the current
|
||||
/// context.
|
||||
unsigned InventedParameterInfosStart = 0;
|
||||
|
||||
ArrayRef<InventedTemplateParameterInfo> getInventedParameterInfos() const {
|
||||
return llvm::makeArrayRef(InventedParameterInfos.begin() +
|
||||
InventedParameterInfosStart,
|
||||
InventedParameterInfos.end());
|
||||
}
|
||||
|
||||
typedef LazyVector<TypedefNameDecl *, ExternalSemaSource,
|
||||
&ExternalSemaSource::ReadExtVectorDecls, 2, 2>
|
||||
ExtVectorDeclsType;
|
||||
@ -800,17 +819,24 @@ class Sema final {
|
||||
DeclContext *SavedContext;
|
||||
ProcessingContextState SavedContextState;
|
||||
QualType SavedCXXThisTypeOverride;
|
||||
unsigned SavedFunctionScopesStart;
|
||||
unsigned SavedInventedParameterInfosStart;
|
||||
|
||||
public:
|
||||
ContextRAII(Sema &S, DeclContext *ContextToPush, bool NewThisContext = true)
|
||||
: S(S), SavedContext(S.CurContext),
|
||||
SavedContextState(S.DelayedDiagnostics.pushUndelayed()),
|
||||
SavedCXXThisTypeOverride(S.CXXThisTypeOverride)
|
||||
SavedCXXThisTypeOverride(S.CXXThisTypeOverride),
|
||||
SavedFunctionScopesStart(S.FunctionScopesStart),
|
||||
SavedInventedParameterInfosStart(S.InventedParameterInfosStart)
|
||||
{
|
||||
assert(ContextToPush && "pushing null context");
|
||||
S.CurContext = ContextToPush;
|
||||
if (NewThisContext)
|
||||
S.CXXThisTypeOverride = QualType();
|
||||
// Any saved FunctionScopes do not refer to this context.
|
||||
S.FunctionScopesStart = S.FunctionScopes.size();
|
||||
S.InventedParameterInfosStart = S.InventedParameterInfos.size();
|
||||
}
|
||||
|
||||
void pop() {
|
||||
@ -818,6 +844,8 @@ class Sema final {
|
||||
S.CurContext = SavedContext;
|
||||
S.DelayedDiagnostics.popUndelayed(SavedContextState);
|
||||
S.CXXThisTypeOverride = SavedCXXThisTypeOverride;
|
||||
S.FunctionScopesStart = SavedFunctionScopesStart;
|
||||
S.InventedParameterInfosStart = SavedInventedParameterInfosStart;
|
||||
SavedContext = nullptr;
|
||||
}
|
||||
|
||||
@ -4924,7 +4952,9 @@ class Sema final {
|
||||
|
||||
void ActOnStartStmtExpr();
|
||||
ExprResult ActOnStmtExpr(Scope *S, SourceLocation LPLoc, Stmt *SubStmt,
|
||||
SourceLocation RPLoc); // "({..})"
|
||||
SourceLocation RPLoc);
|
||||
ExprResult BuildStmtExpr(SourceLocation LPLoc, Stmt *SubStmt,
|
||||
SourceLocation RPLoc, unsigned TemplateDepth);
|
||||
// Handle the final expression in a statement expression.
|
||||
ExprResult ActOnStmtExprResult(ExprResult E);
|
||||
void ActOnStmtExprError();
|
||||
@ -11924,6 +11954,13 @@ class Sema final {
|
||||
return DC;
|
||||
}
|
||||
|
||||
/// Determine the number of levels of enclosing template parameters. This is
|
||||
/// only usable while parsing. Note that this does not include dependent
|
||||
/// contexts in which no template parameters have yet been declared, such as
|
||||
/// in a terse function template or generic lambda before the first 'auto' is
|
||||
/// encountered.
|
||||
unsigned getTemplateDepth(Scope *S) const;
|
||||
|
||||
/// To be used for checking whether the arguments being passed to
|
||||
/// function exceeds the number of parameters expected for it.
|
||||
static bool TooManyArguments(size_t NumParams, size_t NumArgs,
|
||||
|
@ -95,6 +95,16 @@ class VarDecl;
|
||||
return TemplateArgumentLists.size();
|
||||
}
|
||||
|
||||
/// Determine how many of the \p OldDepth outermost template parameter
|
||||
/// lists would be removed by substituting these arguments.
|
||||
unsigned getNewDepth(unsigned OldDepth) const {
|
||||
if (OldDepth < NumRetainedOuterLevels)
|
||||
return OldDepth;
|
||||
if (OldDepth < getNumLevels())
|
||||
return NumRetainedOuterLevels;
|
||||
return OldDepth - TemplateArgumentLists.size();
|
||||
}
|
||||
|
||||
/// Retrieve the template argument at a given depth and index.
|
||||
const TemplateArgument &operator()(unsigned Depth, unsigned Index) const {
|
||||
assert(NumRetainedOuterLevels <= Depth && Depth < getNumLevels());
|
||||
|
@ -6726,7 +6726,7 @@ ExpectedStmt ASTNodeImporter::VisitStmtExpr(StmtExpr *E) {
|
||||
|
||||
return new (Importer.getToContext())
|
||||
StmtExpr(ToSubStmt, ToType, ToLParenLoc, ToRParenLoc,
|
||||
E->isInstantiationDependent());
|
||||
E->getTemplateDepth());
|
||||
}
|
||||
|
||||
ExpectedStmt ASTNodeImporter::VisitUnaryOperator(UnaryOperator *E) {
|
||||
|
@ -42,6 +42,7 @@
|
||||
#include "llvm/ADT/StringRef.h"
|
||||
#include "llvm/Support/Compiler.h"
|
||||
#include "llvm/Support/ErrorHandling.h"
|
||||
#include "llvm/Support/Timer.h"
|
||||
#include <algorithm>
|
||||
#include <cassert>
|
||||
#include <cstddef>
|
||||
@ -1038,6 +1039,8 @@ struct PragmaDebugHandler : public PragmaHandler {
|
||||
if (!PP.getPreprocessorOpts().DisablePragmaDebugCrash)
|
||||
llvm_unreachable("This is an assertion!");
|
||||
} else if (II->isStr("crash")) {
|
||||
llvm::Timer T("crash", "pragma crash");
|
||||
llvm::TimeRegion R(&T);
|
||||
if (!PP.getPreprocessorOpts().DisablePragmaDebugCrash)
|
||||
LLVM_BUILTIN_TRAP;
|
||||
} else if (II->isStr("parser_crash")) {
|
||||
|
@ -13909,7 +13909,12 @@ void Sema::ActOnStmtExprError() {
|
||||
}
|
||||
|
||||
ExprResult Sema::ActOnStmtExpr(Scope *S, SourceLocation LPLoc, Stmt *SubStmt,
|
||||
SourceLocation RPLoc) { // "({..})"
|
||||
SourceLocation RPLoc) {
|
||||
return BuildStmtExpr(LPLoc, SubStmt, RPLoc, getTemplateDepth(S));
|
||||
}
|
||||
|
||||
ExprResult Sema::BuildStmtExpr(SourceLocation LPLoc, Stmt *SubStmt,
|
||||
SourceLocation RPLoc, unsigned TemplateDepth) {
|
||||
assert(SubStmt && isa<CompoundStmt>(SubStmt) && "Invalid action invocation!");
|
||||
CompoundStmt *Compound = cast<CompoundStmt>(SubStmt);
|
||||
|
||||
@ -13938,18 +13943,10 @@ ExprResult Sema::ActOnStmtExpr(Scope *S, SourceLocation LPLoc, Stmt *SubStmt,
|
||||
}
|
||||
}
|
||||
|
||||
bool IsDependentContext = false;
|
||||
if (S)
|
||||
IsDependentContext = S->getTemplateParamParent() != nullptr;
|
||||
else
|
||||
// FIXME: This is not correct when substituting inside a templated
|
||||
// context that isn't a DeclContext (such as a variable template).
|
||||
IsDependentContext = CurContext->isDependentContext();
|
||||
|
||||
// FIXME: Check that expression type is complete/non-abstract; statement
|
||||
// expressions are not lvalues.
|
||||
Expr *ResStmtExpr =
|
||||
new (Context) StmtExpr(Compound, Ty, LPLoc, RPLoc, IsDependentContext);
|
||||
new (Context) StmtExpr(Compound, Ty, LPLoc, RPLoc, TemplateDepth);
|
||||
if (StmtExprMayBindToTemp)
|
||||
return MaybeBindToTemporary(ResStmtExpr);
|
||||
return ResStmtExpr;
|
||||
|
@ -6802,7 +6802,7 @@ Stmt *Sema::MaybeCreateStmtWithCleanups(Stmt *SubStmt) {
|
||||
Context, SubStmt, SourceLocation(), SourceLocation());
|
||||
Expr *E = new (Context)
|
||||
StmtExpr(CompStmt, Context.VoidTy, SourceLocation(), SourceLocation(),
|
||||
CurContext->isDependentContext());
|
||||
/*FIXME TemplateDepth=*/0);
|
||||
return MaybeCreateExprWithCleanups(E);
|
||||
}
|
||||
|
||||
|
@ -46,6 +46,48 @@ clang::getTemplateParamsRange(TemplateParameterList const * const *Ps,
|
||||
return SourceRange(Ps[0]->getTemplateLoc(), Ps[N-1]->getRAngleLoc());
|
||||
}
|
||||
|
||||
unsigned Sema::getTemplateDepth(Scope *S) const {
|
||||
unsigned Depth = 0;
|
||||
|
||||
// Each template parameter scope represents one level of template parameter
|
||||
// depth.
|
||||
for (Scope *TempParamScope = S->getTemplateParamParent();
|
||||
TempParamScope && !Depth;
|
||||
TempParamScope = TempParamScope->getParent()->getTemplateParamParent()) {
|
||||
++Depth;
|
||||
}
|
||||
|
||||
// Note that there are template parameters with the given depth.
|
||||
auto ParamsAtDepth = [&](unsigned D) { Depth = std::max(Depth, D + 1); };
|
||||
|
||||
// Look for parameters of an enclosing generic lambda. We don't create a
|
||||
// template parameter scope for these.
|
||||
for (FunctionScopeInfo *FSI : getFunctionScopes()) {
|
||||
if (auto *LSI = dyn_cast<LambdaScopeInfo>(FSI)) {
|
||||
if (!LSI->TemplateParams.empty()) {
|
||||
ParamsAtDepth(LSI->AutoTemplateParameterDepth);
|
||||
break;
|
||||
}
|
||||
if (LSI->GLTemplateParameterList) {
|
||||
ParamsAtDepth(LSI->GLTemplateParameterList->getDepth());
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Look for parameters of an enclosing terse function template. We don't
|
||||
// create a template parameter scope for these either.
|
||||
for (const InventedTemplateParameterInfo &Info :
|
||||
getInventedParameterInfos()) {
|
||||
if (!Info.TemplateParams.empty()) {
|
||||
ParamsAtDepth(Info.AutoTemplateParameterDepth);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return Depth;
|
||||
}
|
||||
|
||||
/// \brief Determine whether the declaration found is acceptable as the name
|
||||
/// of a template and, if so, return that template declaration. Otherwise,
|
||||
/// returns null.
|
||||
@ -2173,9 +2215,15 @@ struct ConvertConstructorToDeductionGuideTransform {
|
||||
// constructor.
|
||||
ExprResult NewDefArg;
|
||||
if (OldParam->hasDefaultArg()) {
|
||||
NewDefArg = SemaRef.SubstExpr(OldParam->getDefaultArg(), Args);
|
||||
if (NewDefArg.isInvalid())
|
||||
return nullptr;
|
||||
// We don't care what the value is (we won't use it); just create a
|
||||
// placeholder to indicate there is a default argument.
|
||||
QualType ParamTy = NewDI->getType();
|
||||
NewDefArg = new (SemaRef.Context)
|
||||
OpaqueValueExpr(OldParam->getDefaultArg()->getBeginLoc(),
|
||||
ParamTy.getNonLValueExprType(SemaRef.Context),
|
||||
ParamTy->isLValueReferenceType() ? VK_LValue :
|
||||
ParamTy->isRValueReferenceType() ? VK_XValue :
|
||||
VK_RValue);
|
||||
}
|
||||
|
||||
ParmVarDecl *NewParam = ParmVarDecl::Create(SemaRef.Context, DC,
|
||||
|
@ -922,6 +922,10 @@ namespace {
|
||||
this->Entity = Entity;
|
||||
}
|
||||
|
||||
unsigned TransformTemplateDepth(unsigned Depth) {
|
||||
return TemplateArgs.getNewDepth(Depth);
|
||||
}
|
||||
|
||||
bool TryExpandParameterPacks(SourceLocation EllipsisLoc,
|
||||
SourceRange PatternRange,
|
||||
ArrayRef<UnexpandedParameterPack> Unexpanded,
|
||||
@ -2162,7 +2166,7 @@ namespace {
|
||||
// The deduced type itself.
|
||||
TemplateTypeParmDecl *VisitTemplateTypeParmType(
|
||||
const TemplateTypeParmType *T) {
|
||||
if (!T->getDecl()->isImplicit())
|
||||
if (!T->getDecl() || !T->getDecl()->isImplicit())
|
||||
return nullptr;
|
||||
return T->getDecl();
|
||||
}
|
||||
|
@ -212,6 +212,14 @@ class TreeTransform {
|
||||
return T.isNull();
|
||||
}
|
||||
|
||||
/// Transform a template parameter depth level.
|
||||
///
|
||||
/// During a transformation that transforms template parameters, this maps
|
||||
/// an old template parameter depth to a new depth.
|
||||
unsigned TransformTemplateDepth(unsigned Depth) {
|
||||
return Depth;
|
||||
}
|
||||
|
||||
/// Determine whether the given call argument should be dropped, e.g.,
|
||||
/// because it is a default argument.
|
||||
///
|
||||
@ -2527,8 +2535,9 @@ class TreeTransform {
|
||||
/// By default, performs semantic analysis to build the new expression.
|
||||
/// Subclasses may override this routine to provide different behavior.
|
||||
ExprResult RebuildStmtExpr(SourceLocation LParenLoc, Stmt *SubStmt,
|
||||
SourceLocation RParenLoc) {
|
||||
return getSema().ActOnStmtExpr(nullptr, LParenLoc, SubStmt, RParenLoc);
|
||||
SourceLocation RParenLoc, unsigned TemplateDepth) {
|
||||
return getSema().BuildStmtExpr(LParenLoc, SubStmt, RParenLoc,
|
||||
TemplateDepth);
|
||||
}
|
||||
|
||||
/// Build a new __builtin_choose_expr expression.
|
||||
@ -10345,16 +10354,18 @@ TreeTransform<Derived>::TransformStmtExpr(StmtExpr *E) {
|
||||
return ExprError();
|
||||
}
|
||||
|
||||
if (!getDerived().AlwaysRebuild() &&
|
||||
unsigned OldDepth = E->getTemplateDepth();
|
||||
unsigned NewDepth = getDerived().TransformTemplateDepth(OldDepth);
|
||||
|
||||
if (!getDerived().AlwaysRebuild() && OldDepth == NewDepth &&
|
||||
SubStmt.get() == E->getSubStmt()) {
|
||||
// Calling this an 'error' is unintuitive, but it does the right thing.
|
||||
SemaRef.ActOnStmtExprError();
|
||||
return SemaRef.MaybeBindToTemporary(E);
|
||||
}
|
||||
|
||||
return getDerived().RebuildStmtExpr(E->getLParenLoc(),
|
||||
SubStmt.get(),
|
||||
E->getRParenLoc());
|
||||
return getDerived().RebuildStmtExpr(E->getLParenLoc(), SubStmt.get(),
|
||||
E->getRParenLoc(), NewDepth);
|
||||
}
|
||||
|
||||
template<typename Derived>
|
||||
|
@ -2867,7 +2867,8 @@ uint64_t ASTReader::getGlobalBitOffset(ModuleFile &M, uint32_t LocalOffset) {
|
||||
return LocalOffset + M.GlobalBitOffset;
|
||||
}
|
||||
|
||||
static bool isSameTemplateParameterList(const TemplateParameterList *X,
|
||||
static bool isSameTemplateParameterList(const ASTContext &C,
|
||||
const TemplateParameterList *X,
|
||||
const TemplateParameterList *Y);
|
||||
|
||||
/// Determine whether two template parameters are similar enough
|
||||
@ -2879,7 +2880,32 @@ static bool isSameTemplateParameter(const NamedDecl *X,
|
||||
|
||||
if (const auto *TX = dyn_cast<TemplateTypeParmDecl>(X)) {
|
||||
const auto *TY = cast<TemplateTypeParmDecl>(Y);
|
||||
return TX->isParameterPack() == TY->isParameterPack();
|
||||
if (TX->isParameterPack() != TY->isParameterPack())
|
||||
return false;
|
||||
if (TX->hasTypeConstraint() != TY->hasTypeConstraint())
|
||||
return false;
|
||||
if (TX->hasTypeConstraint()) {
|
||||
const TypeConstraint *TXTC = TX->getTypeConstraint();
|
||||
const TypeConstraint *TYTC = TY->getTypeConstraint();
|
||||
if (TXTC->getNamedConcept() != TYTC->getNamedConcept())
|
||||
return false;
|
||||
if (TXTC->hasExplicitTemplateArgs() != TYTC->hasExplicitTemplateArgs())
|
||||
return false;
|
||||
if (TXTC->hasExplicitTemplateArgs()) {
|
||||
const auto *TXTCArgs = TXTC->getTemplateArgsAsWritten();
|
||||
const auto *TYTCArgs = TYTC->getTemplateArgsAsWritten();
|
||||
if (TXTCArgs->NumTemplateArgs != TYTCArgs->NumTemplateArgs)
|
||||
return false;
|
||||
llvm::FoldingSetNodeID XID, YID;
|
||||
for (const auto &ArgLoc : TXTCArgs->arguments())
|
||||
ArgLoc.getArgument().Profile(XID, X->getASTContext());
|
||||
for (const auto &ArgLoc : TYTCArgs->arguments())
|
||||
ArgLoc.getArgument().Profile(YID, Y->getASTContext());
|
||||
if (XID != YID)
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
if (const auto *TX = dyn_cast<NonTypeTemplateParmDecl>(X)) {
|
||||
@ -2891,7 +2917,8 @@ static bool isSameTemplateParameter(const NamedDecl *X,
|
||||
const auto *TX = cast<TemplateTemplateParmDecl>(X);
|
||||
const auto *TY = cast<TemplateTemplateParmDecl>(Y);
|
||||
return TX->isParameterPack() == TY->isParameterPack() &&
|
||||
isSameTemplateParameterList(TX->getTemplateParameters(),
|
||||
isSameTemplateParameterList(TX->getASTContext(),
|
||||
TX->getTemplateParameters(),
|
||||
TY->getTemplateParameters());
|
||||
}
|
||||
|
||||
@ -2944,7 +2971,8 @@ static bool isSameQualifier(const NestedNameSpecifier *X,
|
||||
|
||||
/// Determine whether two template parameter lists are similar enough
|
||||
/// that they may be used in declarations of the same template.
|
||||
static bool isSameTemplateParameterList(const TemplateParameterList *X,
|
||||
static bool isSameTemplateParameterList(const ASTContext &C,
|
||||
const TemplateParameterList *X,
|
||||
const TemplateParameterList *Y) {
|
||||
if (X->size() != Y->size())
|
||||
return false;
|
||||
@ -2953,6 +2981,18 @@ static bool isSameTemplateParameterList(const TemplateParameterList *X,
|
||||
if (!isSameTemplateParameter(X->getParam(I), Y->getParam(I)))
|
||||
return false;
|
||||
|
||||
const Expr *XRC = X->getRequiresClause();
|
||||
const Expr *YRC = Y->getRequiresClause();
|
||||
if (!XRC != !YRC)
|
||||
return false;
|
||||
if (XRC) {
|
||||
llvm::FoldingSetNodeID XRCID, YRCID;
|
||||
XRC->Profile(XRCID, C, /*Canonical=*/true);
|
||||
YRC->Profile(YRCID, C, /*Canonical=*/true);
|
||||
if (XRCID != YRCID)
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
@ -2989,7 +3029,7 @@ static bool hasSameOverloadableAttrs(const FunctionDecl *A,
|
||||
return true;
|
||||
}
|
||||
|
||||
/// Determine whether the two declarations refer to the same entity.
|
||||
/// Determine whether the two declarations refer to the same entity.pr
|
||||
static bool isSameEntity(NamedDecl *X, NamedDecl *Y) {
|
||||
assert(X->getDeclName() == Y->getDeclName() && "Declaration name mismatch!");
|
||||
|
||||
@ -3064,6 +3104,19 @@ static bool isSameEntity(NamedDecl *X, NamedDecl *Y) {
|
||||
}
|
||||
|
||||
ASTContext &C = FuncX->getASTContext();
|
||||
|
||||
const Expr *XRC = FuncX->getTrailingRequiresClause();
|
||||
const Expr *YRC = FuncY->getTrailingRequiresClause();
|
||||
if (!XRC != !YRC)
|
||||
return false;
|
||||
if (XRC) {
|
||||
llvm::FoldingSetNodeID XRCID, YRCID;
|
||||
XRC->Profile(XRCID, C, /*Canonical=*/true);
|
||||
YRC->Profile(YRCID, C, /*Canonical=*/true);
|
||||
if (XRCID != YRCID)
|
||||
return false;
|
||||
}
|
||||
|
||||
auto GetTypeAsWritten = [](const FunctionDecl *FD) {
|
||||
// Map to the first declaration that we've already merged into this one.
|
||||
// The TSI of redeclarations might not match (due to calling conventions
|
||||
@ -3087,6 +3140,7 @@ static bool isSameEntity(NamedDecl *X, NamedDecl *Y) {
|
||||
return true;
|
||||
return false;
|
||||
}
|
||||
|
||||
return FuncX->getLinkageInternal() == FuncY->getLinkageInternal() &&
|
||||
hasSameOverloadableAttrs(FuncX, FuncY);
|
||||
}
|
||||
@ -3126,7 +3180,8 @@ static bool isSameEntity(NamedDecl *X, NamedDecl *Y) {
|
||||
const auto *TemplateY = cast<TemplateDecl>(Y);
|
||||
return isSameEntity(TemplateX->getTemplatedDecl(),
|
||||
TemplateY->getTemplatedDecl()) &&
|
||||
isSameTemplateParameterList(TemplateX->getTemplateParameters(),
|
||||
isSameTemplateParameterList(TemplateX->getASTContext(),
|
||||
TemplateX->getTemplateParameters(),
|
||||
TemplateY->getTemplateParameters());
|
||||
}
|
||||
|
||||
|
@ -754,6 +754,7 @@ void ASTStmtReader::VisitConceptSpecializationExpr(
|
||||
E->TemplateKWLoc = Record.readSourceLocation();
|
||||
E->ConceptName = Record.readDeclarationNameInfo();
|
||||
E->NamedConcept = readDeclAs<ConceptDecl>();
|
||||
E->FoundDecl = Record.readDeclAs<NamedDecl>();
|
||||
E->ArgsAsWritten = Record.readASTTemplateArgumentListInfo();
|
||||
llvm::SmallVector<TemplateArgument, 4> Args;
|
||||
for (unsigned I = 0; I < NumTemplateArgs; ++I)
|
||||
@ -1190,6 +1191,7 @@ void ASTStmtReader::VisitStmtExpr(StmtExpr *E) {
|
||||
E->setLParenLoc(readSourceLocation());
|
||||
E->setRParenLoc(readSourceLocation());
|
||||
E->setSubStmt(cast_or_null<CompoundStmt>(Record.readSubStmt()));
|
||||
E->StmtExprBits.TemplateDepth = Record.readInt();
|
||||
}
|
||||
|
||||
void ASTStmtReader::VisitChooseExpr(ChooseExpr *E) {
|
||||
|
@ -429,6 +429,7 @@ void ASTStmtWriter::VisitConceptSpecializationExpr(
|
||||
Record.AddSourceLocation(E->getTemplateKWLoc());
|
||||
Record.AddDeclarationNameInfo(E->getConceptNameInfo());
|
||||
Record.AddDeclRef(E->getNamedConcept());
|
||||
Record.AddDeclRef(E->getFoundDecl());
|
||||
Record.AddASTTemplateArgumentListInfo(E->getTemplateArgsAsWritten());
|
||||
for (const TemplateArgument &Arg : TemplateArgs)
|
||||
Record.AddTemplateArgument(Arg);
|
||||
@ -1068,6 +1069,7 @@ void ASTStmtWriter::VisitStmtExpr(StmtExpr *E) {
|
||||
Record.AddStmt(E->getSubStmt());
|
||||
Record.AddSourceLocation(E->getLParenLoc());
|
||||
Record.AddSourceLocation(E->getRParenLoc());
|
||||
Record.push_back(E->getTemplateDepth());
|
||||
Code = serialization::EXPR_STMT;
|
||||
}
|
||||
|
||||
|
@ -30,6 +30,7 @@
|
||||
#include "llvm/Option/ArgList.h"
|
||||
#include "llvm/Option/OptTable.h"
|
||||
#include "llvm/Option/Option.h"
|
||||
#include "llvm/Support/BuryPointer.h"
|
||||
#include "llvm/Support/CommandLine.h"
|
||||
#include "llvm/Support/CrashRecoveryContext.h"
|
||||
#include "llvm/Support/ErrorHandling.h"
|
||||
@ -491,6 +492,7 @@ int main(int argc_, const char **argv_) {
|
||||
|
||||
std::unique_ptr<Compilation> C(TheDriver.BuildCompilation(argv));
|
||||
int Res = 1;
|
||||
bool IsCrash = false;
|
||||
if (C && !C->containsError()) {
|
||||
SmallVector<std::pair<int, const Command *>, 4> FailingCommands;
|
||||
Res = TheDriver.ExecuteCompilation(*C, FailingCommands);
|
||||
@ -517,11 +519,11 @@ int main(int argc_, const char **argv_) {
|
||||
// If result status is 70, then the driver command reported a fatal error.
|
||||
// On Windows, abort will return an exit code of 3. In these cases,
|
||||
// generate additional diagnostic information if possible.
|
||||
bool DiagnoseCrash = CommandRes < 0 || CommandRes == 70;
|
||||
IsCrash = CommandRes < 0 || CommandRes == 70;
|
||||
#ifdef _WIN32
|
||||
DiagnoseCrash |= CommandRes == 3;
|
||||
IsCrash |= CommandRes == 3;
|
||||
#endif
|
||||
if (DiagnoseCrash) {
|
||||
if (IsCrash) {
|
||||
TheDriver.generateCompilationDiagnostics(*C, *FailingCommand);
|
||||
break;
|
||||
}
|
||||
@ -530,10 +532,16 @@ int main(int argc_, const char **argv_) {
|
||||
|
||||
Diags.getClient()->finish();
|
||||
|
||||
if (!UseNewCC1Process && IsCrash) {
|
||||
// When crashing in -fintegrated-cc1 mode, bury the timer pointers, because
|
||||
// the internal linked list might point to already released stack frames.
|
||||
llvm::BuryPointer(llvm::TimerGroup::aquireDefaultGroup());
|
||||
} else {
|
||||
// If any timers were active but haven't been destroyed yet, print their
|
||||
// results now. This happens in -disable-free mode.
|
||||
llvm::TimerGroup::printAll(llvm::errs());
|
||||
llvm::TimerGroup::clearAll();
|
||||
}
|
||||
|
||||
#ifdef _WIN32
|
||||
// Exit status should not be negative on Win32, unless abnormal termination.
|
||||
|
@ -102,6 +102,12 @@ class ManagedStatic : public ManagedStaticBase {
|
||||
}
|
||||
|
||||
const C *operator->() const { return &**this; }
|
||||
|
||||
// Extract the instance, leaving the ManagedStatic uninitialized. The
|
||||
// user is then responsible for the lifetime of the returned instance.
|
||||
C *claim() {
|
||||
return static_cast<C *>(Ptr.exchange(nullptr));
|
||||
}
|
||||
};
|
||||
|
||||
/// llvm_shutdown - Deallocate and destroy all ManagedStatic variables.
|
||||
|
@ -230,6 +230,11 @@ class TimerGroup {
|
||||
/// used by the Statistic code to influence the construction and destruction
|
||||
/// order of the global timer lists.
|
||||
static void ConstructTimerLists();
|
||||
|
||||
/// This makes the default group unmanaged, and lets the user manage the
|
||||
/// group's lifetime.
|
||||
static std::unique_ptr<TimerGroup> aquireDefaultGroup();
|
||||
|
||||
private:
|
||||
friend class Timer;
|
||||
friend void PrintStatisticsJSON(raw_ostream &OS);
|
||||
|
@ -441,3 +441,7 @@ const char *TimerGroup::printAllJSONValues(raw_ostream &OS, const char *delim) {
|
||||
void TimerGroup::ConstructTimerLists() {
|
||||
(void)*NamedGroupedTimers;
|
||||
}
|
||||
|
||||
std::unique_ptr<TimerGroup> TimerGroup::aquireDefaultGroup() {
|
||||
return std::unique_ptr<TimerGroup>(DefaultTimerGroup.claim());
|
||||
}
|
||||
|
@ -1,14 +1,14 @@
|
||||
// $FreeBSD$
|
||||
|
||||
#define LLVM_REVISION "llvmorg-10.0.0-rc3-1-gc290cb61fdc"
|
||||
#define LLVM_REVISION "llvmorg-10.0.0-rc4-5-g52c365aa9ca"
|
||||
#define LLVM_REPOSITORY "git@github.com:llvm/llvm-project.git"
|
||||
|
||||
#define CLANG_REVISION "llvmorg-10.0.0-rc3-1-gc290cb61fdc"
|
||||
#define CLANG_REVISION "llvmorg-10.0.0-rc4-5-g52c365aa9ca"
|
||||
#define CLANG_REPOSITORY "git@github.com:llvm/llvm-project.git"
|
||||
|
||||
// <Upstream revision at import>-<Local identifier in __FreeBSD_version style>
|
||||
#define LLD_REVISION "llvmorg-10.0.0-rc3-1-gc290cb61fdc-1300007"
|
||||
#define LLD_REVISION "llvmorg-10.0.0-rc4-5-g52c365aa9ca-1300007"
|
||||
#define LLD_REPOSITORY "FreeBSD"
|
||||
|
||||
#define LLDB_REVISION "llvmorg-10.0.0-rc3-1-gc290cb61fdc"
|
||||
#define LLDB_REVISION "llvmorg-10.0.0-rc4-5-g52c365aa9ca"
|
||||
#define LLDB_REPOSITORY "git@github.com:llvm/llvm-project.git"
|
||||
|
@ -1,3 +1,3 @@
|
||||
/* $FreeBSD$ */
|
||||
#define LLVM_REVISION "llvmorg-10.0.0-rc3-1-gc290cb61fdc"
|
||||
#define LLVM_REVISION "llvmorg-10.0.0-rc4-5-g52c365aa9ca"
|
||||
#define LLVM_REPOSITORY "git@github.com:llvm/llvm-project.git"
|
||||
|
Loading…
Reference in New Issue
Block a user