Renato, Will be fixed ASAP Best regards, Alexey Bataev ============= Software Engineer Intel Compiler Team
09.02.2016 14:07, Renato Golin пишет: > Hi Alexey, > > It's still broken on ARM: > > http://lab.llvm.org:8011/builders/clang-cmake-armv7-a15-full/builds/10409 > > cheers, > --renato > > > On 8 February 2016 at 14:25, Alexey Bataev via cfe-commits > <cfe-commits@lists.llvm.org> wrote: >> Ok, thanks a lot! Hope it will fix win-based buildbots completely. >> >> Best regards, >> Alexey Bataev >> ============= >> Software Engineer >> Intel Compiler Team >> >> 08.02.2016 17:11, NAKAMURA Takumi пишет: >> >> Thanks. It didn't pass with i686-mingw32. >> >> // LAMBDA: call >> // LAMBDA: call{{.*}} void [[OUTER_LAMBDA:@.+]]( >> >> call x86_thiscallcc void @_ZN2SSC1ERi(%struct.SS* %ss, i32* >> dereferenceable(4) @_ZZ4mainE5sivar) >> call x86_thiscallcc void @"_ZZ4mainENK3$_0clEv"(%class.anon* %temp.lvalue) >> >> The latter LAMBDA hit "callcc void @_ZN2SSC1ERi(" >> >> Fixed in r260093. >> >> I suggest like; >> // LAMBDA: call{{.*}} void [[OUTER_LAMBDA:@.+]](%class.anon* >> >> On Mon, Feb 8, 2016 at 10:02 PM Alexey Bataev <a.bat...@hotmail.com> wrote: >>> Yes, I know, will be fixed in few minutes >>> >>> Best regards, >>> Alexey Bataev >>> ============= >>> Software Engineer >>> Intel Compiler Team >>> >>> 08.02.2016 15:43, NAKAMURA Takumi пишет: >>> >>> The test is incompatible to i686-pc-win32. See also >>> http://bb.pgr.jp/builders/ninja-clang-i686-msc18-R/builds/5498 >>> >>> On Mon, Feb 8, 2016 at 6:33 PM Alexey Bataev via cfe-commits >>> <cfe-commits@lists.llvm.org> wrote: >>>> Author: abataev >>>> Date: Mon Feb 8 03:29:13 2016 >>>> New Revision: 260077 >>>> >>>> URL: http://llvm.org/viewvc/llvm-project?rev=260077&view=rev >>>> Log: >>>> [OPENMP 4.5] Ccapture/codegen of private non-static data members. >>>> OpenMP 4.5 introduces privatization of non-static data members of current >>>> class in non-static member functions. >>>> To correctly handle such kind of privatization a new (pseudo)declaration >>>> VarDecl-based node is added. It allows to reuse an existing code for >>>> capturing variables in Lambdas/Block/Captured blocks of code for correct >>>> privatization and codegen. >>>> >>>> Modified: >>>> cfe/trunk/include/clang/AST/DeclOpenMP.h >>>> cfe/trunk/include/clang/AST/RecursiveASTVisitor.h >>>> cfe/trunk/include/clang/Basic/DeclNodes.td >>>> cfe/trunk/include/clang/Sema/Sema.h >>>> cfe/trunk/include/clang/Serialization/ASTBitCodes.h >>>> cfe/trunk/lib/AST/DeclBase.cpp >>>> cfe/trunk/lib/AST/DeclOpenMP.cpp >>>> cfe/trunk/lib/AST/DeclPrinter.cpp >>>> cfe/trunk/lib/AST/StmtPrinter.cpp >>>> cfe/trunk/lib/CodeGen/CGDecl.cpp >>>> cfe/trunk/lib/Sema/SemaExpr.cpp >>>> cfe/trunk/lib/Sema/SemaExprMember.cpp >>>> cfe/trunk/lib/Sema/SemaOpenMP.cpp >>>> cfe/trunk/lib/Sema/SemaTemplateInstantiateDecl.cpp >>>> cfe/trunk/lib/Serialization/ASTCommon.cpp >>>> cfe/trunk/lib/Serialization/ASTReaderDecl.cpp >>>> cfe/trunk/lib/Serialization/ASTWriterDecl.cpp >>>> cfe/trunk/test/OpenMP/parallel_private_codegen.cpp >>>> cfe/trunk/tools/libclang/CIndex.cpp >>>> >>>> Modified: cfe/trunk/include/clang/AST/DeclOpenMP.h >>>> URL: >>>> http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/DeclOpenMP.h?rev=260077&r1=260076&r2=260077&view=diff >>>> >>>> ============================================================================== >>>> --- cfe/trunk/include/clang/AST/DeclOpenMP.h (original) >>>> +++ cfe/trunk/include/clang/AST/DeclOpenMP.h Mon Feb 8 03:29:13 2016 >>>> @@ -87,6 +87,35 @@ public: >>>> static bool classofKind(Kind K) { return K == OMPThreadPrivate; } >>>> }; >>>> >>>> -} // end namespace clang >>>> +/// Pseudo declaration for capturing of non-static data members in >>>> non-static >>>> +/// member functions. >>>> +/// >>>> +/// Clang supports capturing of variables only, but OpenMP 4.5 allows to >>>> +/// privatize non-static members of current class in non-static member >>>> +/// functions. This pseudo-declaration allows properly handle this kind >>>> of >>>> +/// capture by wrapping captured expression into a variable-like >>>> declaration. >>>> +class OMPCapturedFieldDecl final : public VarDecl { >>>> + friend class ASTDeclReader; >>>> + void anchor() override; >>>> + >>>> + OMPCapturedFieldDecl(ASTContext &C, DeclContext *DC, IdentifierInfo >>>> *Id, >>>> + QualType Type) >>>> + : VarDecl(OMPCapturedField, C, DC, SourceLocation(), >>>> SourceLocation(), Id, >>>> + Type, nullptr, SC_None) { >>>> + setImplicit(); >>>> + } >>>> + >>>> +public: >>>> + static OMPCapturedFieldDecl *Create(ASTContext &C, DeclContext *DC, >>>> + IdentifierInfo *Id, QualType T); >>>> + >>>> + static OMPCapturedFieldDecl *CreateDeserialized(ASTContext &C, >>>> unsigned ID); >>>> + >>>> + // Implement isa/cast/dyncast/etc. >>>> + static bool classof(const Decl *D) { return classofKind(D->getKind()); >>>> } >>>> + static bool classofKind(Kind K) { return K == OMPCapturedField; } >>>> +}; >>>> + >>>> +} // end namespace clang >>>> >>>> #endif >>>> >>>> Modified: cfe/trunk/include/clang/AST/RecursiveASTVisitor.h >>>> URL: >>>> http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/RecursiveASTVisitor.h?rev=260077&r1=260076&r2=260077&view=diff >>>> >>>> ============================================================================== >>>> --- cfe/trunk/include/clang/AST/RecursiveASTVisitor.h (original) >>>> +++ cfe/trunk/include/clang/AST/RecursiveASTVisitor.h Mon Feb 8 03:29:13 >>>> 2016 >>>> @@ -1434,6 +1434,8 @@ DEF_TRAVERSE_DECL(OMPThreadPrivateDecl, >>>> } >>>> }) >>>> >>>> +DEF_TRAVERSE_DECL(OMPCapturedFieldDecl, { TRY_TO(TraverseVarHelper(D)); >>>> }) >>>> + >>>> // A helper method for TemplateDecl's children. >>>> template <typename Derived> >>>> bool RecursiveASTVisitor<Derived>::TraverseTemplateParameterListHelper( >>>> >>>> Modified: cfe/trunk/include/clang/Basic/DeclNodes.td >>>> URL: >>>> http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Basic/DeclNodes.td?rev=260077&r1=260076&r2=260077&view=diff >>>> >>>> ============================================================================== >>>> --- cfe/trunk/include/clang/Basic/DeclNodes.td (original) >>>> +++ cfe/trunk/include/clang/Basic/DeclNodes.td Mon Feb 8 03:29:13 2016 >>>> @@ -51,6 +51,7 @@ def Named : Decl<1>; >>>> : DDecl<VarTemplateSpecialization>; >>>> def ImplicitParam : DDecl<Var>; >>>> def ParmVar : DDecl<Var>; >>>> + def OMPCapturedField : DDecl<Var>; >>>> def NonTypeTemplateParm : DDecl<Declarator>; >>>> def Template : DDecl<Named, 1>; >>>> def RedeclarableTemplate : DDecl<Template, 1>; >>>> >>>> Modified: cfe/trunk/include/clang/Sema/Sema.h >>>> URL: >>>> http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Sema/Sema.h?rev=260077&r1=260076&r2=260077&view=diff >>>> >>>> ============================================================================== >>>> --- cfe/trunk/include/clang/Sema/Sema.h (original) >>>> +++ cfe/trunk/include/clang/Sema/Sema.h Mon Feb 8 03:29:13 2016 >>>> @@ -7789,7 +7789,9 @@ public: >>>> /// \brief Check if the specified variable is used in one of the >>>> private >>>> /// clauses (private, firstprivate, lastprivate, reduction etc.) in >>>> OpenMP >>>> /// constructs. >>>> - bool IsOpenMPCapturedDecl(ValueDecl *D); >>>> + VarDecl *IsOpenMPCapturedDecl(ValueDecl *D); >>>> + ExprResult getOpenMPCapturedExpr(VarDecl *Capture, ExprValueKind VK, >>>> + ExprObjectKind OK); >>>> >>>> /// \brief Check if the specified variable is used in 'private' >>>> clause. >>>> /// \param Level Relative level of nested OpenMP construct for that >>>> the check >>>> >>>> Modified: cfe/trunk/include/clang/Serialization/ASTBitCodes.h >>>> URL: >>>> http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Serialization/ASTBitCodes.h?rev=260077&r1=260076&r2=260077&view=diff >>>> >>>> ============================================================================== >>>> --- cfe/trunk/include/clang/Serialization/ASTBitCodes.h (original) >>>> +++ cfe/trunk/include/clang/Serialization/ASTBitCodes.h Mon Feb 8 >>>> 03:29:13 2016 >>>> @@ -1163,6 +1163,8 @@ namespace clang { >>>> DECL_EMPTY, >>>> /// \brief An ObjCTypeParamDecl record. >>>> DECL_OBJC_TYPE_PARAM, >>>> + /// \brief An OMPCapturedFieldDecl record. >>>> + DECL_OMP_CAPTUREDFIELD, >>>> }; >>>> >>>> /// \brief Record codes for each kind of statement or expression. >>>> >>>> Modified: cfe/trunk/lib/AST/DeclBase.cpp >>>> URL: >>>> http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/DeclBase.cpp?rev=260077&r1=260076&r2=260077&view=diff >>>> >>>> ============================================================================== >>>> --- cfe/trunk/lib/AST/DeclBase.cpp (original) >>>> +++ cfe/trunk/lib/AST/DeclBase.cpp Mon Feb 8 03:29:13 2016 >>>> @@ -655,6 +655,7 @@ unsigned Decl::getIdentifierNamespaceFor >>>> case ObjCCategoryImpl: >>>> case Import: >>>> case OMPThreadPrivate: >>>> + case OMPCapturedField: >>>> case Empty: >>>> // Never looked up by name. >>>> return 0; >>>> >>>> Modified: cfe/trunk/lib/AST/DeclOpenMP.cpp >>>> URL: >>>> http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/DeclOpenMP.cpp?rev=260077&r1=260076&r2=260077&view=diff >>>> >>>> ============================================================================== >>>> --- cfe/trunk/lib/AST/DeclOpenMP.cpp (original) >>>> +++ cfe/trunk/lib/AST/DeclOpenMP.cpp Mon Feb 8 03:29:13 2016 >>>> @@ -7,7 +7,8 @@ >>>> // >>>> >>>> //===----------------------------------------------------------------------===// >>>> /// \file >>>> -/// \brief This file implements OMPThreadPrivateDecl class. >>>> +/// \brief This file implements OMPThreadPrivateDecl, >>>> OMPCapturedFieldDecl >>>> +/// classes. >>>> /// >>>> >>>> //===----------------------------------------------------------------------===// >>>> >>>> @@ -52,3 +53,21 @@ void OMPThreadPrivateDecl::setVars(Array >>>> std::uninitialized_copy(VL.begin(), VL.end(), getTrailingObjects<Expr >>>> *>()); >>>> } >>>> >>>> >>>> +//===----------------------------------------------------------------------===// >>>> +// OMPCapturedFieldDecl Implementation. >>>> >>>> +//===----------------------------------------------------------------------===// >>>> + >>>> +void OMPCapturedFieldDecl::anchor() {} >>>> + >>>> +OMPCapturedFieldDecl *OMPCapturedFieldDecl::Create(ASTContext &C, >>>> + DeclContext *DC, >>>> + IdentifierInfo *Id, >>>> + QualType T) { >>>> + return new (C, DC) OMPCapturedFieldDecl(C, DC, Id, T); >>>> +} >>>> + >>>> +OMPCapturedFieldDecl >>>> *OMPCapturedFieldDecl::CreateDeserialized(ASTContext &C, >>>> + unsigned >>>> ID) { >>>> + return new (C, ID) OMPCapturedFieldDecl(C, nullptr, nullptr, >>>> QualType()); >>>> +} >>>> + >>>> >>>> Modified: cfe/trunk/lib/AST/DeclPrinter.cpp >>>> URL: >>>> http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/DeclPrinter.cpp?rev=260077&r1=260076&r2=260077&view=diff >>>> >>>> ============================================================================== >>>> --- cfe/trunk/lib/AST/DeclPrinter.cpp (original) >>>> +++ cfe/trunk/lib/AST/DeclPrinter.cpp Mon Feb 8 03:29:13 2016 >>>> @@ -92,6 +92,7 @@ namespace { >>>> void VisitUsingDecl(UsingDecl *D); >>>> void VisitUsingShadowDecl(UsingShadowDecl *D); >>>> void VisitOMPThreadPrivateDecl(OMPThreadPrivateDecl *D); >>>> + void VisitOMPCapturedFieldDecl(OMPCapturedFieldDecl *D); >>>> >>>> void PrintTemplateParameters(const TemplateParameterList *Params, >>>> const TemplateArgumentList *Args = >>>> nullptr); >>>> @@ -1366,3 +1367,7 @@ void DeclPrinter::VisitOMPThreadPrivateD >>>> } >>>> } >>>> >>>> +void DeclPrinter::VisitOMPCapturedFieldDecl(OMPCapturedFieldDecl *D) { >>>> + D->getInit()->printPretty(Out, nullptr, Policy, Indentation); >>>> +} >>>> + >>>> >>>> Modified: cfe/trunk/lib/AST/StmtPrinter.cpp >>>> URL: >>>> http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/StmtPrinter.cpp?rev=260077&r1=260076&r2=260077&view=diff >>>> >>>> ============================================================================== >>>> --- cfe/trunk/lib/AST/StmtPrinter.cpp (original) >>>> +++ cfe/trunk/lib/AST/StmtPrinter.cpp Mon Feb 8 03:29:13 2016 >>>> @@ -16,6 +16,7 @@ >>>> #include "clang/AST/Attr.h" >>>> #include "clang/AST/DeclCXX.h" >>>> #include "clang/AST/DeclObjC.h" >>>> +#include "clang/AST/DeclOpenMP.h" >>>> #include "clang/AST/DeclTemplate.h" >>>> #include "clang/AST/Expr.h" >>>> #include "clang/AST/ExprCXX.h" >>>> @@ -763,15 +764,16 @@ template<typename T> >>>> void OMPClausePrinter::VisitOMPClauseList(T *Node, char StartSym) { >>>> for (typename T::varlist_iterator I = Node->varlist_begin(), >>>> E = Node->varlist_end(); >>>> - I != E; ++I) { >>>> + I != E; ++I) { >>>> assert(*I && "Expected non-null Stmt"); >>>> + OS << (I == Node->varlist_begin() ? StartSym : ','); >>>> if (DeclRefExpr *DRE = dyn_cast<DeclRefExpr>(*I)) { >>>> - OS << (I == Node->varlist_begin() ? StartSym : ','); >>>> - cast<NamedDecl>(DRE->getDecl())->printQualifiedName(OS); >>>> - } else { >>>> - OS << (I == Node->varlist_begin() ? StartSym : ','); >>>> + if (auto *CFD = dyn_cast<OMPCapturedFieldDecl>(DRE->getDecl())) >>>> + CFD->getInit()->IgnoreImpCasts()->printPretty(OS, nullptr, >>>> Policy, 0); >>>> + else >>>> + DRE->getDecl()->printQualifiedName(OS); >>>> + } else >>>> (*I)->printPretty(OS, nullptr, Policy, 0); >>>> - } >>>> } >>>> } >>>> >>>> >>>> Modified: cfe/trunk/lib/CodeGen/CGDecl.cpp >>>> URL: >>>> http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CGDecl.cpp?rev=260077&r1=260076&r2=260077&view=diff >>>> >>>> ============================================================================== >>>> --- cfe/trunk/lib/CodeGen/CGDecl.cpp (original) >>>> +++ cfe/trunk/lib/CodeGen/CGDecl.cpp Mon Feb 8 03:29:13 2016 >>>> @@ -92,6 +92,7 @@ void CodeGenFunction::EmitDecl(const Dec >>>> case Decl::Label: // __label__ x; >>>> case Decl::Import: >>>> case Decl::OMPThreadPrivate: >>>> + case Decl::OMPCapturedField: >>>> case Decl::Empty: >>>> // None of these decls require codegen support. >>>> return; >>>> >>>> Modified: cfe/trunk/lib/Sema/SemaExpr.cpp >>>> URL: >>>> http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaExpr.cpp?rev=260077&r1=260076&r2=260077&view=diff >>>> >>>> ============================================================================== >>>> --- cfe/trunk/lib/Sema/SemaExpr.cpp (original) >>>> +++ cfe/trunk/lib/Sema/SemaExpr.cpp Mon Feb 8 03:29:13 2016 >>>> @@ -2874,6 +2874,7 @@ ExprResult Sema::BuildDeclarationNameExp >>>> case Decl::Var: >>>> case Decl::VarTemplateSpecialization: >>>> case Decl::VarTemplatePartialSpecialization: >>>> + case Decl::OMPCapturedField: >>>> // In C, "extern void blah;" is valid and is an r-value. >>>> if (!getLangOpts().CPlusPlus && >>>> !type.hasQualifiers() && >>>> >>>> Modified: cfe/trunk/lib/Sema/SemaExprMember.cpp >>>> URL: >>>> http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaExprMember.cpp?rev=260077&r1=260076&r2=260077&view=diff >>>> >>>> ============================================================================== >>>> --- cfe/trunk/lib/Sema/SemaExprMember.cpp (original) >>>> +++ cfe/trunk/lib/Sema/SemaExprMember.cpp Mon Feb 8 03:29:13 2016 >>>> @@ -1735,9 +1735,19 @@ BuildFieldReferenceExpr(Sema &S, Expr *B >>>> FoundDecl, Field); >>>> if (Base.isInvalid()) >>>> return ExprError(); >>>> - return BuildMemberExpr(S, S.Context, Base.get(), IsArrow, OpLoc, SS, >>>> - /*TemplateKWLoc=*/SourceLocation(), Field, >>>> FoundDecl, >>>> - MemberNameInfo, MemberType, VK, OK); >>>> + MemberExpr *ME = >>>> + BuildMemberExpr(S, S.Context, Base.get(), IsArrow, OpLoc, SS, >>>> + /*TemplateKWLoc=*/SourceLocation(), Field, >>>> FoundDecl, >>>> + MemberNameInfo, MemberType, VK, OK); >>>> + >>>> + // Build a reference to a private copy for non-static data members in >>>> + // non-static member functions, privatized by OpenMP constructs. >>>> + if (S.getLangOpts().OpenMP && IsArrow && >>>> + isa<CXXThisExpr>(Base.get()->IgnoreParenImpCasts())) { >>>> + if (auto *PrivateCopy = S.IsOpenMPCapturedDecl(Field)) >>>> + return S.getOpenMPCapturedExpr(PrivateCopy, VK, OK); >>>> + } >>>> + return ME; >>>> } >>>> >>>> /// Builds an implicit member access expression. The current context >>>> >>>> Modified: cfe/trunk/lib/Sema/SemaOpenMP.cpp >>>> URL: >>>> http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaOpenMP.cpp?rev=260077&r1=260076&r2=260077&view=diff >>>> >>>> ============================================================================== >>>> --- cfe/trunk/lib/Sema/SemaOpenMP.cpp (original) >>>> +++ cfe/trunk/lib/Sema/SemaOpenMP.cpp Mon Feb 8 03:29:13 2016 >>>> @@ -71,10 +71,11 @@ public: >>>> OpenMPDirectiveKind DKind; >>>> OpenMPClauseKind CKind; >>>> Expr *RefExpr; >>>> + DeclRefExpr *PrivateCopy; >>>> SourceLocation ImplicitDSALoc; >>>> DSAVarData() >>>> : DKind(OMPD_unknown), CKind(OMPC_unknown), RefExpr(nullptr), >>>> - ImplicitDSALoc() {} >>>> + PrivateCopy(nullptr), ImplicitDSALoc() {} >>>> }; >>>> >>>> private: >>>> @@ -83,11 +84,12 @@ private: >>>> struct DSAInfo { >>>> OpenMPClauseKind Attributes; >>>> Expr *RefExpr; >>>> + DeclRefExpr *PrivateCopy; >>>> }; >>>> - typedef llvm::SmallDenseMap<ValueDecl *, DSAInfo, 64> DeclSAMapTy; >>>> - typedef llvm::SmallDenseMap<ValueDecl *, Expr *, 64> AlignedMapTy; >>>> + typedef llvm::DenseMap<ValueDecl *, DSAInfo> DeclSAMapTy; >>>> + typedef llvm::DenseMap<ValueDecl *, Expr *> AlignedMapTy; >>>> typedef llvm::DenseMap<ValueDecl *, unsigned> >>>> LoopControlVariablesMapTy; >>>> - typedef llvm::SmallDenseMap<ValueDecl *, MapInfo, 64> MappedDeclsTy; >>>> + typedef llvm::DenseMap<ValueDecl *, MapInfo> MappedDeclsTy; >>>> typedef llvm::StringMap<std::pair<OMPCriticalDirective *, >>>> llvm::APSInt>> >>>> CriticalsWithHintsTy; >>>> >>>> @@ -195,7 +197,8 @@ public: >>>> ValueDecl *getParentLoopControlVariable(unsigned I); >>>> >>>> /// \brief Adds explicit data sharing attribute to the specified >>>> declaration. >>>> - void addDSA(ValueDecl *D, Expr *E, OpenMPClauseKind A); >>>> + void addDSA(ValueDecl *D, Expr *E, OpenMPClauseKind A, >>>> + DeclRefExpr *PrivateCopy = nullptr); >>>> >>>> /// \brief Returns data sharing attributes from top of the stack for >>>> the >>>> /// specified declaration. >>>> @@ -434,6 +437,7 @@ DSAStackTy::DSAVarData DSAStackTy::getDS >>>> // attributes. >>>> if (Iter->SharingMap.count(D)) { >>>> DVar.RefExpr = Iter->SharingMap[D].RefExpr; >>>> + DVar.PrivateCopy = Iter->SharingMap[D].PrivateCopy; >>>> DVar.CKind = Iter->SharingMap[D].Attributes; >>>> DVar.ImplicitDSALoc = Iter->DefaultAttrLoc; >>>> return DVar; >>>> @@ -547,15 +551,20 @@ ValueDecl *DSAStackTy::getParentLoopCont >>>> return nullptr; >>>> } >>>> >>>> -void DSAStackTy::addDSA(ValueDecl *D, Expr *E, OpenMPClauseKind A) { >>>> +void DSAStackTy::addDSA(ValueDecl *D, Expr *E, OpenMPClauseKind A, >>>> + DeclRefExpr *PrivateCopy) { >>>> D = getCanonicalDecl(D); >>>> if (A == OMPC_threadprivate) { >>>> Stack[0].SharingMap[D].Attributes = A; >>>> Stack[0].SharingMap[D].RefExpr = E; >>>> + Stack[0].SharingMap[D].PrivateCopy = nullptr; >>>> } else { >>>> assert(Stack.size() > 1 && "Data-sharing attributes stack is >>>> empty"); >>>> Stack.back().SharingMap[D].Attributes = A; >>>> Stack.back().SharingMap[D].RefExpr = E; >>>> + Stack.back().SharingMap[D].PrivateCopy = PrivateCopy; >>>> + if (PrivateCopy) >>>> + addDSA(PrivateCopy->getDecl(), PrivateCopy, A); >>>> } >>>> } >>>> >>>> @@ -682,6 +691,7 @@ DSAStackTy::DSAVarData DSAStackTy::getTo >>>> auto I = std::prev(StartI); >>>> if (I->SharingMap.count(D)) { >>>> DVar.RefExpr = I->SharingMap[D].RefExpr; >>>> + DVar.PrivateCopy = I->SharingMap[D].PrivateCopy; >>>> DVar.CKind = I->SharingMap[D].Attributes; >>>> DVar.ImplicitDSALoc = I->DefaultAttrLoc; >>>> } >>>> @@ -886,7 +896,7 @@ bool Sema::IsOpenMPCapturedByRef(ValueDe >>>> return IsByRef; >>>> } >>>> >>>> -bool Sema::IsOpenMPCapturedDecl(ValueDecl *D) { >>>> +VarDecl *Sema::IsOpenMPCapturedDecl(ValueDecl *D) { >>>> assert(LangOpts.OpenMP && "OpenMP is not allowed"); >>>> D = getCanonicalDecl(D); >>>> >>>> @@ -900,18 +910,16 @@ bool Sema::IsOpenMPCapturedDecl(ValueDec >>>> auto *VD = dyn_cast<VarDecl>(D); >>>> if (VD && !VD->hasLocalStorage()) { >>>> if (DSAStack->getCurrentDirective() == OMPD_target && >>>> - !DSAStack->isClauseParsingMode()) { >>>> - return true; >>>> - } >>>> + !DSAStack->isClauseParsingMode()) >>>> + return VD; >>>> if (DSAStack->getCurScope() && >>>> DSAStack->hasDirective( >>>> [](OpenMPDirectiveKind K, const DeclarationNameInfo &DNI, >>>> SourceLocation Loc) -> bool { >>>> return isOpenMPTargetExecutionDirective(K); >>>> }, >>>> - false)) { >>>> - return true; >>>> - } >>>> + false)) >>>> + return VD; >>>> } >>>> >>>> if (DSAStack->getCurrentDirective() != OMPD_unknown && >>>> @@ -921,15 +929,16 @@ bool Sema::IsOpenMPCapturedDecl(ValueDec >>>> (VD && VD->hasLocalStorage() && >>>> isParallelOrTaskRegion(DSAStack->getCurrentDirective())) || >>>> (VD && DSAStack->isForceVarCapturing())) >>>> - return true; >>>> + return VD; >>>> auto DVarPrivate = DSAStack->getTopDSA(D, >>>> DSAStack->isClauseParsingMode()); >>>> if (DVarPrivate.CKind != OMPC_unknown && >>>> isOpenMPPrivate(DVarPrivate.CKind)) >>>> - return true; >>>> + return VD ? VD : >>>> cast<VarDecl>(DVarPrivate.PrivateCopy->getDecl()); >>>> DVarPrivate = DSAStack->hasDSA(D, isOpenMPPrivate, MatchesAlways(), >>>> DSAStack->isClauseParsingMode()); >>>> - return DVarPrivate.CKind != OMPC_unknown; >>>> + if (DVarPrivate.CKind != OMPC_unknown) >>>> + return VD ? VD : >>>> cast<VarDecl>(DVarPrivate.PrivateCopy->getDecl()); >>>> } >>>> - return false; >>>> + return nullptr; >>>> } >>>> >>>> bool Sema::isOpenMPPrivateDecl(ValueDecl *D, unsigned Level) { >>>> @@ -6958,6 +6967,50 @@ OMPClause *Sema::ActOnOpenMPVarListClaus >>>> return Res; >>>> } >>>> >>>> +static DeclRefExpr *buildCapture(Sema &S, IdentifierInfo *Id, >>>> + Expr *CaptureExpr) { >>>> + ASTContext &C = S.getASTContext(); >>>> + Expr *Init = CaptureExpr->IgnoreImpCasts(); >>>> + QualType Ty = Init->getType(); >>>> + if (CaptureExpr->getObjectKind() == OK_Ordinary) { >>>> + if (S.getLangOpts().CPlusPlus) >>>> + Ty = C.getLValueReferenceType(Ty); >>>> + else { >>>> + Ty = C.getPointerType(Ty); >>>> + ExprResult Res = >>>> + S.CreateBuiltinUnaryOp(CaptureExpr->getExprLoc(), UO_AddrOf, >>>> Init); >>>> + if (!Res.isUsable()) >>>> + return nullptr; >>>> + Init = Res.get(); >>>> + } >>>> + } >>>> + auto *CFD = OMPCapturedFieldDecl::Create(C, S.CurContext, Id, Ty); >>>> + S.CurContext->addHiddenDecl(CFD); >>>> + S.AddInitializerToDecl(CFD, Init, /*DirectInit=*/false, >>>> + /*TypeMayContainAuto=*/true); >>>> + return buildDeclRefExpr(S, CFD, Ty.getNonReferenceType(), >>>> SourceLocation()); >>>> +} >>>> + >>>> +ExprResult Sema::getOpenMPCapturedExpr(VarDecl *Capture, ExprValueKind >>>> VK, >>>> + ExprObjectKind OK) { >>>> + SourceLocation Loc = Capture->getInit()->getExprLoc(); >>>> + ExprResult Res = BuildDeclRefExpr( >>>> + Capture, Capture->getType().getNonReferenceType(), VK_LValue, >>>> Loc); >>>> + if (!Res.isUsable()) >>>> + return ExprError(); >>>> + if (OK == OK_Ordinary && !getLangOpts().CPlusPlus) { >>>> + Res = CreateBuiltinUnaryOp(Loc, UO_Deref, Res.get()); >>>> + if (!Res.isUsable()) >>>> + return ExprError(); >>>> + } >>>> + if (VK != VK_LValue && Res.get()->isGLValue()) { >>>> + Res = DefaultLvalueConversion(Res.get()); >>>> + if (!Res.isUsable()) >>>> + return ExprError(); >>>> + } >>>> + return Res; >>>> +} >>>> + >>>> OMPClause *Sema::ActOnOpenMPPrivateClause(ArrayRef<Expr *> VarList, >>>> SourceLocation StartLoc, >>>> SourceLocation LParenLoc, >>>> @@ -7050,8 +7103,11 @@ OMPClause *Sema::ActOnOpenMPPrivateClaus >>>> auto VDPrivateRefExpr = buildDeclRefExpr( >>>> *this, VDPrivate, RefExpr->getType().getUnqualifiedType(), >>>> ELoc); >>>> >>>> - DSAStack->addDSA(D, RefExpr->IgnoreParens(), OMPC_private); >>>> - Vars.push_back(RefExpr->IgnoreParens()); >>>> + DeclRefExpr *Ref = nullptr; >>>> + if (!VD) >>>> + Ref = buildCapture(*this, D->getIdentifier(), RefExpr); >>>> + DSAStack->addDSA(D, RefExpr->IgnoreParens(), OMPC_private, Ref); >>>> + Vars.push_back(VD ? RefExpr->IgnoreParens() : Ref); >>>> PrivateCopies.push_back(VDPrivateRefExpr); >>>> } >>>> >>>> >>>> Modified: cfe/trunk/lib/Sema/SemaTemplateInstantiateDecl.cpp >>>> URL: >>>> http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaTemplateInstantiateDecl.cpp?rev=260077&r1=260076&r2=260077&view=diff >>>> >>>> ============================================================================== >>>> --- cfe/trunk/lib/Sema/SemaTemplateInstantiateDecl.cpp (original) >>>> +++ cfe/trunk/lib/Sema/SemaTemplateInstantiateDecl.cpp Mon Feb 8 >>>> 03:29:13 2016 >>>> @@ -2483,6 +2483,11 @@ Decl *TemplateDeclInstantiator::VisitOMP >>>> return TD; >>>> } >>>> >>>> +Decl *TemplateDeclInstantiator::VisitOMPCapturedFieldDecl( >>>> + OMPCapturedFieldDecl * /*D*/) { >>>> + llvm_unreachable("Should not be met in templates"); >>>> +} >>>> + >>>> Decl *TemplateDeclInstantiator::VisitFunctionDecl(FunctionDecl *D) { >>>> return VisitFunctionDecl(D, nullptr); >>>> } >>>> >>>> Modified: cfe/trunk/lib/Serialization/ASTCommon.cpp >>>> URL: >>>> http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Serialization/ASTCommon.cpp?rev=260077&r1=260076&r2=260077&view=diff >>>> >>>> ============================================================================== >>>> --- cfe/trunk/lib/Serialization/ASTCommon.cpp (original) >>>> +++ cfe/trunk/lib/Serialization/ASTCommon.cpp Mon Feb 8 03:29:13 2016 >>>> @@ -329,6 +329,7 @@ bool serialization::isRedeclarableDeclKi >>>> case Decl::ClassScopeFunctionSpecialization: >>>> case Decl::Import: >>>> case Decl::OMPThreadPrivate: >>>> + case Decl::OMPCapturedField: >>>> case Decl::BuiltinTemplate: >>>> return false; >>>> >>>> >>>> Modified: cfe/trunk/lib/Serialization/ASTReaderDecl.cpp >>>> URL: >>>> http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Serialization/ASTReaderDecl.cpp?rev=260077&r1=260076&r2=260077&view=diff >>>> >>>> ============================================================================== >>>> --- cfe/trunk/lib/Serialization/ASTReaderDecl.cpp (original) >>>> +++ cfe/trunk/lib/Serialization/ASTReaderDecl.cpp Mon Feb 8 03:29:13 >>>> 2016 >>>> @@ -350,6 +350,7 @@ namespace clang { >>>> void VisitObjCPropertyDecl(ObjCPropertyDecl *D); >>>> void VisitObjCPropertyImplDecl(ObjCPropertyImplDecl *D); >>>> void VisitOMPThreadPrivateDecl(OMPThreadPrivateDecl *D); >>>> + void VisitOMPCapturedFieldDecl(OMPCapturedFieldDecl *D); >>>> >>>> /// We've merged the definition \p MergedDef into the existing >>>> definition >>>> /// \p Def. Ensure that \p Def is made visible whenever \p MergedDef >>>> is made >>>> @@ -2360,6 +2361,10 @@ void ASTDeclReader::VisitOMPThreadPrivat >>>> D->setVars(Vars); >>>> } >>>> >>>> +void ASTDeclReader::VisitOMPCapturedFieldDecl(OMPCapturedFieldDecl *D) { >>>> + VisitVarDecl(D); >>>> +} >>>> + >>>> >>>> //===----------------------------------------------------------------------===// >>>> // Attribute Reading >>>> >>>> //===----------------------------------------------------------------------===// >>>> @@ -3323,6 +3328,9 @@ Decl *ASTReader::ReadDeclRecord(DeclID I >>>> case DECL_OMP_THREADPRIVATE: >>>> D = OMPThreadPrivateDecl::CreateDeserialized(Context, ID, >>>> Record[Idx++]); >>>> break; >>>> + case DECL_OMP_CAPTUREDFIELD: >>>> + D = OMPCapturedFieldDecl::CreateDeserialized(Context, ID); >>>> + break; >>>> case DECL_EMPTY: >>>> D = EmptyDecl::CreateDeserialized(Context, ID); >>>> break; >>>> >>>> Modified: cfe/trunk/lib/Serialization/ASTWriterDecl.cpp >>>> URL: >>>> http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Serialization/ASTWriterDecl.cpp?rev=260077&r1=260076&r2=260077&view=diff >>>> >>>> ============================================================================== >>>> --- cfe/trunk/lib/Serialization/ASTWriterDecl.cpp (original) >>>> +++ cfe/trunk/lib/Serialization/ASTWriterDecl.cpp Mon Feb 8 03:29:13 >>>> 2016 >>>> @@ -131,6 +131,7 @@ namespace clang { >>>> void VisitObjCPropertyDecl(ObjCPropertyDecl *D); >>>> void VisitObjCPropertyImplDecl(ObjCPropertyImplDecl *D); >>>> void VisitOMPThreadPrivateDecl(OMPThreadPrivateDecl *D); >>>> + void VisitOMPCapturedFieldDecl(OMPCapturedFieldDecl *D); >>>> >>>> /// Add an Objective-C type parameter list to the given record. >>>> void AddObjCTypeParamList(ObjCTypeParamList *typeParams) { >>>> @@ -1628,6 +1629,11 @@ void ASTDeclWriter::VisitOMPThreadPrivat >>>> Code = serialization::DECL_OMP_THREADPRIVATE; >>>> } >>>> >>>> +void ASTDeclWriter::VisitOMPCapturedFieldDecl(OMPCapturedFieldDecl *D) { >>>> + VisitVarDecl(D); >>>> + Code = serialization::DECL_OMP_CAPTUREDFIELD; >>>> +} >>>> + >>>> >>>> //===----------------------------------------------------------------------===// >>>> // ASTWriter Implementation >>>> >>>> //===----------------------------------------------------------------------===// >>>> >>>> Modified: cfe/trunk/test/OpenMP/parallel_private_codegen.cpp >>>> URL: >>>> http://llvm.org/viewvc/llvm-project/cfe/trunk/test/OpenMP/parallel_private_codegen.cpp?rev=260077&r1=260076&r2=260077&view=diff >>>> >>>> ============================================================================== >>>> --- cfe/trunk/test/OpenMP/parallel_private_codegen.cpp (original) >>>> +++ cfe/trunk/test/OpenMP/parallel_private_codegen.cpp Mon Feb 8 >>>> 03:29:13 2016 >>>> @@ -18,11 +18,69 @@ struct S { >>>> >>>> volatile int g __attribute__((aligned(128))) = 1212; >>>> >>>> +struct SS { >>>> + int a; >>>> + int b : 4; >>>> + int &c; >>>> + SS(int &d) : a(0), b(0), c(d) { >>>> +#pragma omp parallel private(a, b, c) >>>> +#ifdef LAMBDA >>>> + [&]() { >>>> + ++this->a, --b, (this)->c /= 1; >>>> +#pragma omp parallel private(a, b, c) >>>> + ++(this)->a, --b, this->c /= 1; >>>> + }(); >>>> +#elif defined(BLOCKS) >>>> + ^{ >>>> + ++a; >>>> + --this->b; >>>> + (this)->c /= 1; >>>> +#pragma omp parallel private(a, b, c) >>>> + ++(this)->a, --b, this->c /= 1; >>>> + }(); >>>> +#else >>>> + ++this->a, --b, c /= 1; >>>> +#endif >>>> + } >>>> +}; >>>> + >>>> +template<typename T> >>>> +struct SST { >>>> + T a; >>>> + SST() : a(T()) { >>>> +#pragma omp parallel private(a) >>>> +#ifdef LAMBDA >>>> + [&]() { >>>> + [&]() { >>>> + ++this->a; >>>> +#pragma omp parallel private(a) >>>> + ++(this)->a; >>>> + }(); >>>> + }(); >>>> +#elif defined(BLOCKS) >>>> + ^{ >>>> + ^{ >>>> + ++a; >>>> +#pragma omp parallel private(a) >>>> + ++(this)->a; >>>> + }(); >>>> + }(); >>>> +#else >>>> + ++(this)->a; >>>> +#endif >>>> + } >>>> +}; >>>> + >>>> +// CHECK: [[SS_TY:%.+]] = type { i{{[0-9]+}}, i8 >>>> +// LAMBDA: [[SS_TY:%.+]] = type { i{{[0-9]+}}, i8 >>>> +// BLOCKS: [[SS_TY:%.+]] = type { i{{[0-9]+}}, i8 >>>> // CHECK: [[S_FLOAT_TY:%.+]] = type { float } >>>> // CHECK: [[S_INT_TY:%.+]] = type { i{{[0-9]+}} } >>>> +// CHECK: [[SST_TY:%.+]] = type { i{{[0-9]+}} } >>>> template <typename T> >>>> T tmain() { >>>> S<T> test; >>>> + SST<T> sst; >>>> T t_var __attribute__((aligned(128))) = T(); >>>> T vec[] __attribute__((aligned(128))) = {1, 2}; >>>> S<T> s_arr[] __attribute__((aligned(128))) = {1, 2}; >>>> @@ -37,9 +95,11 @@ T tmain() { >>>> >>>> int main() { >>>> static int sivar; >>>> + SS ss(sivar); >>>> #ifdef LAMBDA >>>> // LAMBDA: [[G:@.+]] = global i{{[0-9]+}} 1212, >>>> // LAMBDA-LABEL: @main >>>> + // LAMBDA: call >>>> // LAMBDA: call{{.*}} void [[OUTER_LAMBDA:@.+]]( >>>> [&]() { >>>> // LAMBDA: define{{.*}} internal{{.*}} void [[OUTER_LAMBDA]]( >>>> @@ -47,6 +107,36 @@ int main() { >>>> // LAMBDA: call{{.*}} void {{.+}} @__kmpc_fork_call({{.+}}, i32 0, >>>> {{.+}}* [[OMP_REGION:@.+]] to {{.+}}) >>>> #pragma omp parallel private(g, sivar) >>>> { >>>> + // LAMBDA: define {{.+}} @{{.+}}([[SS_TY]]* % >>>> + // LAMBDA: store i{{[0-9]+}} 0, i{{[0-9]+}}* % >>>> + // LAMBDA: store i8 >>>> + // LAMBDA: call void (%{{.+}}*, i{{[0-9]+}}, void (i{{[0-9]+}}*, >>>> i{{[0-9]+}}*, ...)*, ...) @__kmpc_fork_call(%{{.+}}* @{{.+}}, i{{[0-9]+}} >>>> 1, >>>> void (i{{[0-9]+}}*, i{{[0-9]+}}*, ...)* bitcast (void (i{{[0-9]+}}*, >>>> i{{[0-9]+}}*, [[SS_TY]]*)* [[SS_MICROTASK:@.+]] to void >>>> + // LAMBDA: ret >>>> + >>>> + // LAMBDA: define internal void [[SS_MICROTASK]](i{{[0-9]+}}* >>>> noalias [[GTID_ADDR:%.+]], i{{[0-9]+}}* noalias %{{.+}}, [[SS_TY]]* >>>> %{{.+}}) >>>> + // LAMBDA-NOT: getelementptr {{.*}}[[SS_TY]], [[SS_TY]]* % >>>> + // LAMBDA: call{{.*}} void >>>> + // LAMBDA: ret void >>>> + >>>> + // LAMBDA: define internal void @{{.+}}(i{{[0-9]+}}* noalias >>>> [[GTID_ADDR:%.+]], i{{[0-9]+}}* noalias %{{.+}}, [[SS_TY]]* %{{.+}}) >>>> + // LAMBDA: [[A_PRIV:%.+]] = alloca i{{[0-9]+}}, >>>> + // LAMBDA: [[B_PRIV:%.+]] = alloca i{{[0-9]+}}, >>>> + // LAMBDA: [[C_PRIV:%.+]] = alloca i{{[0-9]+}}, >>>> + // LAMBDA: store i{{[0-9]+}}* [[A_PRIV]], i{{[0-9]+}}** >>>> [[REFA:%.+]], >>>> + // LAMBDA: store i{{[0-9]+}}* [[C_PRIV]], i{{[0-9]+}}** >>>> [[REFC:%.+]], >>>> + // LAMBDA-NEXT: [[A_PRIV:%.+]] = load i{{[0-9]+}}*, i{{[0-9]+}}** >>>> [[REFA]], >>>> + // LAMBDA-NEXT: [[A_VAL:%.+]] = load i{{[0-9]+}}, i{{[0-9]+}}* >>>> [[A_PRIV]], >>>> + // LAMBDA-NEXT: [[INC:%.+]] = add nsw i{{[0-9]+}} [[A_VAL]], 1 >>>> + // LAMBDA-NEXT: store i{{[0-9]+}} [[INC]], i{{[0-9]+}}* [[A_PRIV]], >>>> + // LAMBDA-NEXT: [[B_VAL:%.+]] = load i{{[0-9]+}}, i{{[0-9]+}}* >>>> [[B_PRIV]], >>>> + // LAMBDA-NEXT: [[DEC:%.+]] = add nsw i{{[0-9]+}} [[B_VAL]], -1 >>>> + // LAMBDA-NEXT: store i{{[0-9]+}} [[DEC]], i{{[0-9]+}}* [[B_PRIV]], >>>> + // LAMBDA-NEXT: [[C_PRIV:%.+]] = load i{{[0-9]+}}*, i{{[0-9]+}}** >>>> [[REFC]], >>>> + // LAMBDA-NEXT: [[C_VAL:%.+]] = load i{{[0-9]+}}, i{{[0-9]+}}* >>>> [[C_PRIV]], >>>> + // LAMBDA-NEXT: [[DIV:%.+]] = sdiv i{{[0-9]+}} [[C_VAL]], 1 >>>> + // LAMBDA-NEXT: store i{{[0-9]+}} [[DIV]], i{{[0-9]+}}* [[C_PRIV]], >>>> + // LAMBDA-NEXT: ret void >>>> + >>>> // LAMBDA: define{{.*}} internal{{.*}} void [[OMP_REGION]](i32* >>>> noalias %{{.+}}, i32* noalias %{{.+}}) >>>> // LAMBDA: [[G_PRIVATE_ADDR:%.+]] = alloca i{{[0-9]+}}, >>>> // LAMBDA: [[SIVAR_PRIVATE_ADDR:%.+]] = alloca i{{[0-9]+}}, >>>> @@ -80,6 +170,7 @@ int main() { >>>> #elif defined(BLOCKS) >>>> // BLOCKS: [[G:@.+]] = global i{{[0-9]+}} 1212, >>>> // BLOCKS-LABEL: @main >>>> + // BLOCKS: call >>>> // BLOCKS: call{{.*}} void {{%.+}}(i8 >>>> ^{ >>>> // BLOCKS: define{{.*}} internal{{.*}} void {{.+}}(i8* >>>> @@ -116,6 +207,35 @@ int main() { >>>> } >>>> }(); >>>> return 0; >>>> +// BLOCKS: define {{.+}} @{{.+}}([[SS_TY]]* % >>>> +// BLOCKS: store i{{[0-9]+}} 0, i{{[0-9]+}}* % >>>> +// BLOCKS: store i8 >>>> +// BLOCKS: call void (%{{.+}}*, i{{[0-9]+}}, void (i{{[0-9]+}}*, >>>> i{{[0-9]+}}*, ...)*, ...) @__kmpc_fork_call(%{{.+}}* @{{.+}}, i{{[0-9]+}} >>>> 1, >>>> void (i{{[0-9]+}}*, i{{[0-9]+}}*, ...)* bitcast (void (i{{[0-9]+}}*, >>>> i{{[0-9]+}}*, [[SS_TY]]*)* [[SS_MICROTASK:@.+]] to void >>>> +// BLOCKS: ret >>>> + >>>> +// BLOCKS: define internal void [[SS_MICROTASK]](i{{[0-9]+}}* noalias >>>> [[GTID_ADDR:%.+]], i{{[0-9]+}}* noalias %{{.+}}, [[SS_TY]]* %{{.+}}) >>>> +// BLOCKS-NOT: getelementptr {{.*}}[[SS_TY]], [[SS_TY]]* % >>>> +// BLOCKS: call{{.*}} void >>>> +// BLOCKS: ret void >>>> + >>>> +// BLOCKS: define internal void @{{.+}}(i{{[0-9]+}}* noalias >>>> [[GTID_ADDR:%.+]], i{{[0-9]+}}* noalias %{{.+}}, [[SS_TY]]* %{{.+}}) >>>> +// BLOCKS: [[A_PRIV:%.+]] = alloca i{{[0-9]+}}, >>>> +// BLOCKS: [[B_PRIV:%.+]] = alloca i{{[0-9]+}}, >>>> +// BLOCKS: [[C_PRIV:%.+]] = alloca i{{[0-9]+}}, >>>> +// BLOCKS: store i{{[0-9]+}}* [[A_PRIV]], i{{[0-9]+}}** [[REFA:%.+]], >>>> +// BLOCKS: store i{{[0-9]+}}* [[C_PRIV]], i{{[0-9]+}}** [[REFC:%.+]], >>>> +// BLOCKS-NEXT: [[A_PRIV:%.+]] = load i{{[0-9]+}}*, i{{[0-9]+}}** >>>> [[REFA]], >>>> +// BLOCKS-NEXT: [[A_VAL:%.+]] = load i{{[0-9]+}}, i{{[0-9]+}}* >>>> [[A_PRIV]], >>>> +// BLOCKS-NEXT: [[INC:%.+]] = add nsw i{{[0-9]+}} [[A_VAL]], 1 >>>> +// BLOCKS-NEXT: store i{{[0-9]+}} [[INC]], i{{[0-9]+}}* [[A_PRIV]], >>>> +// BLOCKS-NEXT: [[B_VAL:%.+]] = load i{{[0-9]+}}, i{{[0-9]+}}* >>>> [[B_PRIV]], >>>> +// BLOCKS-NEXT: [[DEC:%.+]] = add nsw i{{[0-9]+}} [[B_VAL]], -1 >>>> +// BLOCKS-NEXT: store i{{[0-9]+}} [[DEC]], i{{[0-9]+}}* [[B_PRIV]], >>>> +// BLOCKS-NEXT: [[C_PRIV:%.+]] = load i{{[0-9]+}}*, i{{[0-9]+}}** >>>> [[REFC]], >>>> +// BLOCKS-NEXT: [[C_VAL:%.+]] = load i{{[0-9]+}}, i{{[0-9]+}}* >>>> [[C_PRIV]], >>>> +// BLOCKS-NEXT: [[DIV:%.+]] = sdiv i{{[0-9]+}} [[C_VAL]], 1 >>>> +// BLOCKS-NEXT: store i{{[0-9]+}} [[DIV]], i{{[0-9]+}}* [[C_PRIV]], >>>> +// BLOCKS-NEXT: ret void >>>> #else >>>> S<float> test; >>>> int t_var = 0; >>>> @@ -166,6 +286,31 @@ int main() { >>>> // CHECK: call void [[S_INT_TY_DESTR:@.+]]([[S_INT_TY]]* >>>> // CHECK: ret >>>> // >>>> +// CHECK: define {{.+}} @{{.+}}([[SS_TY]]* % >>>> +// CHECK: store i{{[0-9]+}} 0, i{{[0-9]+}}* % >>>> +// CHECK: store i8 >>>> +// CHECK: call void (%{{.+}}*, i{{[0-9]+}}, void (i{{[0-9]+}}*, >>>> i{{[0-9]+}}*, ...)*, ...) @__kmpc_fork_call(%{{.+}}* @{{.+}}, i{{[0-9]+}} >>>> 1, >>>> void (i{{[0-9]+}}*, i{{[0-9]+}}*, ...)* bitcast (void (i{{[0-9]+}}*, >>>> i{{[0-9]+}}*, [[SS_TY]]*)* [[SS_MICROTASK:@.+]] to void >>>> +// CHECK: ret >>>> + >>>> +// CHECK: define internal void [[SS_MICROTASK]](i{{[0-9]+}}* noalias >>>> [[GTID_ADDR:%.+]], i{{[0-9]+}}* noalias %{{.+}}, [[SS_TY]]* %{{.+}}) >>>> +// CHECK: [[A_PRIV:%.+]] = alloca i{{[0-9]+}}, >>>> +// CHECK: [[B_PRIV:%.+]] = alloca i{{[0-9]+}}, >>>> +// CHECK: [[C_PRIV:%.+]] = alloca i{{[0-9]+}}, >>>> +// CHECK: store i{{[0-9]+}}* [[A_PRIV]], i{{[0-9]+}}** [[REFA:%.+]], >>>> +// CHECK: store i{{[0-9]+}}* [[C_PRIV]], i{{[0-9]+}}** [[REFC:%.+]], >>>> +// CHECK-NEXT: [[A_PRIV:%.+]] = load i{{[0-9]+}}*, i{{[0-9]+}}** >>>> [[REFA]], >>>> +// CHECK-NEXT: [[A_VAL:%.+]] = load i{{[0-9]+}}, i{{[0-9]+}}* >>>> [[A_PRIV]], >>>> +// CHECK-NEXT: [[INC:%.+]] = add nsw i{{[0-9]+}} [[A_VAL]], 1 >>>> +// CHECK-NEXT: store i{{[0-9]+}} [[INC]], i{{[0-9]+}}* [[A_PRIV]], >>>> +// CHECK-NEXT: [[B_VAL:%.+]] = load i{{[0-9]+}}, i{{[0-9]+}}* >>>> [[B_PRIV]], >>>> +// CHECK-NEXT: [[DEC:%.+]] = add nsw i{{[0-9]+}} [[B_VAL]], -1 >>>> +// CHECK-NEXT: store i{{[0-9]+}} [[DEC]], i{{[0-9]+}}* [[B_PRIV]], >>>> +// CHECK-NEXT: [[C_PRIV:%.+]] = load i{{[0-9]+}}*, i{{[0-9]+}}** >>>> [[REFC]], >>>> +// CHECK-NEXT: [[C_VAL:%.+]] = load i{{[0-9]+}}, i{{[0-9]+}}* >>>> [[C_PRIV]], >>>> +// CHECK-NEXT: [[DIV:%.+]] = sdiv i{{[0-9]+}} [[C_VAL]], 1 >>>> +// CHECK-NEXT: store i{{[0-9]+}} [[DIV]], i{{[0-9]+}}* [[C_PRIV]], >>>> +// CHECK-NEXT: ret void >>>> + >>>> // CHECK: define internal void [[TMAIN_MICROTASK]](i{{[0-9]+}}* noalias >>>> [[GTID_ADDR:%.+]], i{{[0-9]+}}* noalias %{{.+}}) >>>> // CHECK: [[T_VAR_PRIV:%.+]] = alloca i{{[0-9]+}}, align 128 >>>> // CHECK: [[VEC_PRIV:%.+]] = alloca [2 x i{{[0-9]+}}], align 128 >>>> @@ -184,5 +329,20 @@ int main() { >>>> // CHECK-DAG: call void [[S_INT_TY_DESTR]]([[S_INT_TY]]* [[VAR_PRIV]]) >>>> // CHECK-DAG: call void [[S_INT_TY_DESTR]]([[S_INT_TY]]* >>>> // CHECK: ret void >>>> + >>>> +// CHECK: define {{.+}} @{{.+}}([[SST_TY]]* % >>>> +// CHECK: store i{{[0-9]+}} 0, i{{[0-9]+}}* % >>>> +// CHECK: call void (%{{.+}}*, i{{[0-9]+}}, void (i{{[0-9]+}}*, >>>> i{{[0-9]+}}*, ...)*, ...) @__kmpc_fork_call(%{{.+}}* @{{.+}}, i{{[0-9]+}} >>>> 1, >>>> void (i{{[0-9]+}}*, i{{[0-9]+}}*, ...)* bitcast (void (i{{[0-9]+}}*, >>>> i{{[0-9]+}}*, [[SST_TY]]*)* [[SST_MICROTASK:@.+]] to void >>>> +// CHECK: ret >>>> + >>>> +// CHECK: define internal void [[SST_MICROTASK]](i{{[0-9]+}}* noalias >>>> [[GTID_ADDR:%.+]], i{{[0-9]+}}* noalias %{{.+}}, [[SST_TY]]* %{{.+}}) >>>> +// CHECK: [[A_PRIV:%.+]] = alloca i{{[0-9]+}}, >>>> +// CHECK: store i{{[0-9]+}}* [[A_PRIV]], i{{[0-9]+}}** [[REF:%.+]], >>>> +// CHECK-NEXT: [[A_PRIV:%.+]] = load i{{[0-9]+}}*, i{{[0-9]+}}** >>>> [[REF]], >>>> +// CHECK-NEXT: [[A_VAL:%.+]] = load i{{[0-9]+}}, i{{[0-9]+}}* >>>> [[A_PRIV]], >>>> +// CHECK-NEXT: [[INC:%.+]] = add nsw i{{[0-9]+}} [[A_VAL]], 1 >>>> +// CHECK-NEXT: store i{{[0-9]+}} [[INC]], i{{[0-9]+}}* [[A_PRIV]], >>>> +// CHECK-NEXT: ret void >>>> + >>>> #endif >>>> >>>> >>>> Modified: cfe/trunk/tools/libclang/CIndex.cpp >>>> URL: >>>> http://llvm.org/viewvc/llvm-project/cfe/trunk/tools/libclang/CIndex.cpp?rev=260077&r1=260076&r2=260077&view=diff >>>> >>>> ============================================================================== >>>> --- cfe/trunk/tools/libclang/CIndex.cpp (original) >>>> +++ cfe/trunk/tools/libclang/CIndex.cpp Mon Feb 8 03:29:13 2016 >>>> @@ -5669,6 +5669,7 @@ CXCursor clang_getCursorDefinition(CXCur >>>> case Decl::StaticAssert: >>>> case Decl::Block: >>>> case Decl::Captured: >>>> + case Decl::OMPCapturedField: >>>> case Decl::Label: // FIXME: Is this right?? >>>> case Decl::ClassScopeFunctionSpecialization: >>>> case Decl::Import: >>>> >>>> >>>> _______________________________________________ >>>> cfe-commits mailing list >>>> cfe-commits@lists.llvm.org >>>> http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits >>> >> >> _______________________________________________ >> cfe-commits mailing list >> cfe-commits@lists.llvm.org >> http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits >> _______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits