<div dir="ltr">Thanks.</div><div class="gmail_extra"><br><div class="gmail_quote">On Wed, Oct 21, 2015 at 12:14 PM, Benjamin Kramer <span dir="ltr"><<a href="mailto:benny.kra@gmail.com" target="_blank">benny.kra@gmail.com</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">Reverted for now in r250889.<br>
<div class="HOEnZb"><div class="h5"><br>
On Wed, Oct 21, 2015 at 12:07 PM, Daniel Jasper <<a href="mailto:djasper@google.com">djasper@google.com</a>> wrote:<br>
> I think we'll need to come up with a different solution. The problem is that<br>
> DynTypedNode is 5 times larger than the bare pointer and we are storing many<br>
> more elements in the ParentMap. This means, this change is effectively<br>
> increasing the parent map by 10x and it was already large to begin with.<br>
><br>
> Please revert and lets come up with a different solution.<br>
><br>
> On Tue, Oct 20, 2015 at 5:08 PM, Benjamin Kramer via cfe-commits<br>
> <<a href="mailto:cfe-commits@lists.llvm.org">cfe-commits@lists.llvm.org</a>> wrote:<br>
>><br>
>> Author: d0k<br>
>> Date: Tue Oct 20 10:08:46 2015<br>
>> New Revision: 250831<br>
>><br>
>> URL: <a href="http://llvm.org/viewvc/llvm-project?rev=250831&view=rev" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project?rev=250831&view=rev</a><br>
>> Log:<br>
>> [AST] Put TypeLocs and NestedNameSpecifierLocs into the ParentMap.<br>
>><br>
>> Firstly this changes the type of parent map to be keyed on DynTypedNode to<br>
>> simplify the following changes. This comes with a DenseMapInfo for<br>
>> DynTypedNode, which is a bit incomplete still and will probably only work<br>
>> for parentmap right now.<br>
>><br>
>> Then the RecursiveASTVisitor in ASTContext is updated and finally<br>
>> ASTMatchers hasParent and hasAncestor learn about the new functionality.<br>
>><br>
>> Now ParentMap is only missing TemplateArgumentLocs and<br>
>> CXXCtorInitializers.<br>
>><br>
>> Differential Revision: <a href="http://reviews.llvm.org/D13897" rel="noreferrer" target="_blank">http://reviews.llvm.org/D13897</a><br>
>><br>
>> Modified:<br>
>> cfe/trunk/include/clang/AST/ASTContext.h<br>
>> cfe/trunk/include/clang/AST/ASTTypeTraits.h<br>
>> cfe/trunk/include/clang/ASTMatchers/ASTMatchers.h<br>
>> cfe/trunk/include/clang/ASTMatchers/ASTMatchersInternal.h<br>
>> cfe/trunk/lib/AST/ASTContext.cpp<br>
>> cfe/trunk/lib/ASTMatchers/ASTMatchFinder.cpp<br>
>> cfe/trunk/unittests/AST/ASTContextParentMapTest.cpp<br>
>> cfe/trunk/unittests/ASTMatchers/Dynamic/ParserTest.cpp<br>
>> cfe/trunk/unittests/ASTMatchers/Dynamic/RegistryTest.cpp<br>
>><br>
>> Modified: cfe/trunk/include/clang/AST/ASTContext.h<br>
>> URL:<br>
>> <a href="http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/ASTContext.h?rev=250831&r1=250830&r2=250831&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/ASTContext.h?rev=250831&r1=250830&r2=250831&view=diff</a><br>
>><br>
>> ==============================================================================<br>
>> --- cfe/trunk/include/clang/AST/ASTContext.h (original)<br>
>> +++ cfe/trunk/include/clang/AST/ASTContext.h Tue Oct 20 10:08:46 2015<br>
>> @@ -452,7 +452,7 @@ public:<br>
>> typedef llvm::SmallVector<ast_type_traits::DynTypedNode, 2><br>
>> ParentVector;<br>
>><br>
>> /// \brief Maps from a node to its parents.<br>
>> - typedef llvm::DenseMap<const void *,<br>
>> + typedef llvm::DenseMap<ast_type_traits::DynTypedNode,<br>
>> llvm::PointerUnion<ast_type_traits::DynTypedNode<br>
>> *,<br>
>> ParentVector *>> ParentMap;<br>
>><br>
>><br>
>> Modified: cfe/trunk/include/clang/AST/ASTTypeTraits.h<br>
>> URL:<br>
>> <a href="http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/ASTTypeTraits.h?rev=250831&r1=250830&r2=250831&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/ASTTypeTraits.h?rev=250831&r1=250830&r2=250831&view=diff</a><br>
>><br>
>> ==============================================================================<br>
>> --- cfe/trunk/include/clang/AST/ASTTypeTraits.h (original)<br>
>> +++ cfe/trunk/include/clang/AST/ASTTypeTraits.h Tue Oct 20 10:08:46 2015<br>
>> @@ -253,10 +253,30 @@ public:<br>
>> /// @{<br>
>> /// \brief Imposes an order on \c DynTypedNode.<br>
>> ///<br>
>> - /// Supports comparison of nodes that support memoization.<br>
>> - /// FIXME: Implement comparsion for other node types (currently<br>
>> - /// only Stmt, Decl, Type and NestedNameSpecifier return memoization<br>
>> data).<br>
>> + /// FIXME: Implement comparsion for other node types.<br>
>> bool operator<(const DynTypedNode &Other) const {<br>
>> + if (!NodeKind.isSame(Other.NodeKind))<br>
>> + return NodeKind < Other.NodeKind;<br>
>> +<br>
>> + if (ASTNodeKind::getFromNodeKind<TypeLoc>().isSame(NodeKind)) {<br>
>> + auto TLA = getUnchecked<TypeLoc>();<br>
>> + auto TLB = Other.getUnchecked<TypeLoc>();<br>
>> + return std::make_pair(TLA.getType().getAsOpaquePtr(),<br>
>> + TLA.getOpaqueData()) <<br>
>> + std::make_pair(TLB.getType().getAsOpaquePtr(),<br>
>> + TLB.getOpaqueData());<br>
>> + }<br>
>> +<br>
>> + if (ASTNodeKind::getFromNodeKind<NestedNameSpecifierLoc>().isSame(<br>
>> + NodeKind)) {<br>
>> + auto NNSLA = getUnchecked<NestedNameSpecifierLoc>();<br>
>> + auto NNSLB = Other.getUnchecked<NestedNameSpecifierLoc>();<br>
>> + return std::make_pair(NNSLA.getNestedNameSpecifier(),<br>
>> + NNSLA.getOpaqueData()) <<br>
>> + std::make_pair(NNSLB.getNestedNameSpecifier(),<br>
>> + NNSLB.getOpaqueData());<br>
>> + }<br>
>> +<br>
>> assert(getMemoizationData() && Other.getMemoizationData());<br>
>> return getMemoizationData() < Other.getMemoizationData();<br>
>> }<br>
>> @@ -270,6 +290,13 @@ public:<br>
>> if (ASTNodeKind::getFromNodeKind<QualType>().isSame(NodeKind))<br>
>> return getUnchecked<QualType>() == Other.getUnchecked<QualType>();<br>
>><br>
>> + if (ASTNodeKind::getFromNodeKind<TypeLoc>().isSame(NodeKind))<br>
>> + return getUnchecked<TypeLoc>() == Other.getUnchecked<TypeLoc>();<br>
>> +<br>
>> + if<br>
>> (ASTNodeKind::getFromNodeKind<NestedNameSpecifierLoc>().isSame(NodeKind))<br>
>> + return getUnchecked<NestedNameSpecifierLoc>() ==<br>
>> + Other.getUnchecked<NestedNameSpecifierLoc>();<br>
>> +<br>
>> assert(getMemoizationData() && Other.getMemoizationData());<br>
>> return getMemoizationData() == Other.getMemoizationData();<br>
>> }<br>
>> @@ -278,6 +305,47 @@ public:<br>
>> }<br>
>> /// @}<br>
>><br>
>> + /// \brief Hooks for using DynTypedNode as a key in a DenseMap.<br>
>> + struct DenseMapInfo {<br>
>> + static inline DynTypedNode getEmptyKey() {<br>
>> + DynTypedNode Node;<br>
>> + Node.NodeKind = ASTNodeKind::DenseMapInfo::getEmptyKey();<br>
>> + return Node;<br>
>> + }<br>
>> + static inline DynTypedNode getTombstoneKey() {<br>
>> + DynTypedNode Node;<br>
>> + Node.NodeKind = ASTNodeKind::DenseMapInfo::getTombstoneKey();<br>
>> + return Node;<br>
>> + }<br>
>> + static unsigned getHashValue(const DynTypedNode &Val) {<br>
>> + // FIXME: Add hashing support for the remaining types.<br>
>> + if (ASTNodeKind::getFromNodeKind<TypeLoc>().isSame(Val.NodeKind)) {<br>
>> + auto TL = Val.getUnchecked<TypeLoc>();<br>
>> + return llvm::hash_combine(TL.getType().getAsOpaquePtr(),<br>
>> + TL.getOpaqueData());<br>
>> + }<br>
>> +<br>
>> + if (ASTNodeKind::getFromNodeKind<NestedNameSpecifierLoc>().isSame(<br>
>> + Val.NodeKind)) {<br>
>> + auto NNSL = Val.getUnchecked<NestedNameSpecifierLoc>();<br>
>> + return llvm::hash_combine(NNSL.getNestedNameSpecifier(),<br>
>> + NNSL.getOpaqueData());<br>
>> + }<br>
>> +<br>
>> + assert(Val.getMemoizationData());<br>
>> + return llvm::hash_value(Val.getMemoizationData());<br>
>> + }<br>
>> + static bool isEqual(const DynTypedNode &LHS, const DynTypedNode &RHS)<br>
>> {<br>
>> + auto Empty = ASTNodeKind::DenseMapInfo::getEmptyKey();<br>
>> + auto TombStone = ASTNodeKind::DenseMapInfo::getTombstoneKey();<br>
>> + return (ASTNodeKind::DenseMapInfo::isEqual(LHS.NodeKind, Empty) &&<br>
>> + ASTNodeKind::DenseMapInfo::isEqual(RHS.NodeKind, Empty)) ||<br>
>> + (ASTNodeKind::DenseMapInfo::isEqual(LHS.NodeKind, TombStone)<br>
>> &&<br>
>> + ASTNodeKind::DenseMapInfo::isEqual(RHS.NodeKind,<br>
>> TombStone)) ||<br>
>> + LHS == RHS;<br>
>> + }<br>
>> + };<br>
>> +<br>
>> private:<br>
>> /// \brief Takes care of converting from and to \c T.<br>
>> template <typename T, typename EnablerT = void> struct BaseConverter;<br>
>> @@ -420,6 +488,10 @@ template <><br>
>> struct DenseMapInfo<clang::ast_type_traits::ASTNodeKind><br>
>> : clang::ast_type_traits::ASTNodeKind::DenseMapInfo {};<br>
>><br>
>> +template <><br>
>> +struct DenseMapInfo<clang::ast_type_traits::DynTypedNode><br>
>> + : clang::ast_type_traits::DynTypedNode::DenseMapInfo {};<br>
>> +<br>
>> } // end namespace llvm<br>
>><br>
>> #endif<br>
>><br>
>> Modified: cfe/trunk/include/clang/ASTMatchers/ASTMatchers.h<br>
>> URL:<br>
>> <a href="http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/ASTMatchers/ASTMatchers.h?rev=250831&r1=250830&r2=250831&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/ASTMatchers/ASTMatchers.h?rev=250831&r1=250830&r2=250831&view=diff</a><br>
>><br>
>> ==============================================================================<br>
>> --- cfe/trunk/include/clang/ASTMatchers/ASTMatchers.h (original)<br>
>> +++ cfe/trunk/include/clang/ASTMatchers/ASTMatchers.h Tue Oct 20 10:08:46<br>
>> 2015<br>
>> @@ -2068,8 +2068,10 @@ internal::Matcher<T> findAll(const inter<br>
>> ///<br>
>> /// Usable as: Any Matcher<br>
>> const internal::ArgumentAdaptingMatcherFunc<<br>
>> - internal::HasParentMatcher, internal::TypeList<Decl, Stmt>,<br>
>> - internal::TypeList<Decl, Stmt> > LLVM_ATTRIBUTE_UNUSED hasParent =<br>
>> {};<br>
>> + internal::HasParentMatcher,<br>
>> + internal::TypeList<Decl, NestedNameSpecifierLoc, Stmt, TypeLoc>,<br>
>> + internal::TypeList<Decl, NestedNameSpecifierLoc, Stmt, TypeLoc>><br>
>> + LLVM_ATTRIBUTE_UNUSED hasParent = {};<br>
>><br>
>> /// \brief Matches AST nodes that have an ancestor that matches the<br>
>> provided<br>
>> /// matcher.<br>
>> @@ -2083,8 +2085,10 @@ const internal::ArgumentAdaptingMatcherF<br>
>> ///<br>
>> /// Usable as: Any Matcher<br>
>> const internal::ArgumentAdaptingMatcherFunc<<br>
>> - internal::HasAncestorMatcher, internal::TypeList<Decl, Stmt>,<br>
>> - internal::TypeList<Decl, Stmt> > LLVM_ATTRIBUTE_UNUSED hasAncestor =<br>
>> {};<br>
>> + internal::HasAncestorMatcher,<br>
>> + internal::TypeList<Decl, NestedNameSpecifierLoc, Stmt, TypeLoc>,<br>
>> + internal::TypeList<Decl, NestedNameSpecifierLoc, Stmt, TypeLoc>><br>
>> + LLVM_ATTRIBUTE_UNUSED hasAncestor = {};<br>
>><br>
>> /// \brief Matches if the provided matcher does not match.<br>
>> ///<br>
>><br>
>> Modified: cfe/trunk/include/clang/ASTMatchers/ASTMatchersInternal.h<br>
>> URL:<br>
>> <a href="http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/ASTMatchers/ASTMatchersInternal.h?rev=250831&r1=250830&r2=250831&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/ASTMatchers/ASTMatchersInternal.h?rev=250831&r1=250830&r2=250831&view=diff</a><br>
>><br>
>> ==============================================================================<br>
>> --- cfe/trunk/include/clang/ASTMatchers/ASTMatchersInternal.h (original)<br>
>> +++ cfe/trunk/include/clang/ASTMatchers/ASTMatchersInternal.h Tue Oct 20<br>
>> 10:08:46 2015<br>
>> @@ -848,8 +848,10 @@ public:<br>
>> BoundNodesTreeBuilder *Builder,<br>
>> AncestorMatchMode MatchMode) {<br>
>> static_assert(std::is_base_of<Decl, T>::value ||<br>
>> - std::is_base_of<Stmt, T>::value,<br>
>> - "only Decl or Stmt allowed for recursive matching");<br>
>> + std::is_base_of<NestedNameSpecifierLoc, T>::value<br>
>> ||<br>
>> + std::is_base_of<Stmt, T>::value ||<br>
>> + std::is_base_of<TypeLoc, T>::value,<br>
>> + "type not allowed for recursive matching");<br>
>> return matchesAncestorOf(ast_type_traits::DynTypedNode::create(Node),<br>
>> Matcher, Builder, MatchMode);<br>
>> }<br>
>><br>
>> Modified: cfe/trunk/lib/AST/ASTContext.cpp<br>
>> URL:<br>
>> <a href="http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/ASTContext.cpp?rev=250831&r1=250830&r2=250831&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/ASTContext.cpp?rev=250831&r1=250830&r2=250831&view=diff</a><br>
>><br>
>> ==============================================================================<br>
>> --- cfe/trunk/lib/AST/ASTContext.cpp (original)<br>
>> +++ cfe/trunk/lib/AST/ASTContext.cpp Tue Oct 20 10:08:46 2015<br>
>> @@ -8678,6 +8678,23 @@ bool ASTContext::AtomicUsesUnsupportedLi<br>
>><br>
>> namespace {<br>
>><br>
>> +/// Template specializations to abstract away from pointers and TypeLocs.<br>
>> +/// @{<br>
>> +template <typename T><br>
>> +ast_type_traits::DynTypedNode createDynTypedNode(const T &Node) {<br>
>> + return ast_type_traits::DynTypedNode::create(*Node);<br>
>> +}<br>
>> +template <><br>
>> +ast_type_traits::DynTypedNode createDynTypedNode(const TypeLoc &Node) {<br>
>> + return ast_type_traits::DynTypedNode::create(Node);<br>
>> +}<br>
>> +template <><br>
>> +ast_type_traits::DynTypedNode<br>
>> +createDynTypedNode(const NestedNameSpecifierLoc &Node) {<br>
>> + return ast_type_traits::DynTypedNode::create(Node);<br>
>> +}<br>
>> +/// @}<br>
>> +<br>
>> /// \brief A \c RecursiveASTVisitor that builds a map from nodes to<br>
>> their<br>
>> /// parents as defined by the \c RecursiveASTVisitor.<br>
>> ///<br>
>> @@ -8685,7 +8702,8 @@ namespace {<br>
>> /// traversal - there are other relationships (for example declaration<br>
>> context)<br>
>> /// in the AST that are better modeled by special matchers.<br>
>> ///<br>
>> - /// FIXME: Currently only builds up the map using \c Stmt and \c Decl<br>
>> nodes.<br>
>> +/// FIXME: Currently only builds up the map using \c Stmt, \c Decl,<br>
>> +/// \c NestedNameSpecifierLoc and \c TypeLoc nodes.<br>
>> class ParentMapASTVisitor : public<br>
>> RecursiveASTVisitor<ParentMapASTVisitor> {<br>
>><br>
>> public:<br>
>> @@ -8717,21 +8735,11 @@ namespace {<br>
>> }<br>
>><br>
>> template <typename T><br>
>> - bool TraverseNode(T *Node, bool(VisitorBase:: *traverse) (T *)) {<br>
>> + bool TraverseNode(T Node, bool (VisitorBase::*traverse)(T)) {<br>
>> if (!Node)<br>
>> return true;<br>
>> if (ParentStack.size() > 0) {<br>
>> - // FIXME: Currently we add the same parent multiple times, but<br>
>> only<br>
>> - // when no memoization data is available for the type.<br>
>> - // For example when we visit all subexpressions of template<br>
>> - // instantiations; this is suboptimal, but benign: the only way<br>
>> to<br>
>> - // visit those is with hasAncestor / hasParent, and those do not<br>
>> create<br>
>> - // new matches.<br>
>> - // The plan is to enable DynTypedNode to be storable in a map or<br>
>> hash<br>
>> - // map. The main problem there is to implement hash functions /<br>
>> - // comparison operators for all types that DynTypedNode supports<br>
>> that<br>
>> - // do not have pointer identity.<br>
>> - auto &NodeOrVector = (*Parents)[Node];<br>
>> + auto &NodeOrVector = (*Parents)[createDynTypedNode(Node)];<br>
>> if (NodeOrVector.isNull()) {<br>
>> NodeOrVector = new<br>
>> ast_type_traits::DynTypedNode(ParentStack.back());<br>
>> } else {<br>
>> @@ -8757,7 +8765,7 @@ namespace {<br>
>> Vector->push_back(ParentStack.back());<br>
>> }<br>
>> }<br>
>> -<br>
>> ParentStack.push_back(ast_type_traits::DynTypedNode::create(*Node));<br>
>> + ParentStack.push_back(createDynTypedNode(Node));<br>
>> bool Result = (this ->* traverse) (Node);<br>
>> ParentStack.pop_back();<br>
>> return Result;<br>
>> @@ -8771,6 +8779,15 @@ namespace {<br>
>> return TraverseNode(StmtNode, &VisitorBase::TraverseStmt);<br>
>> }<br>
>><br>
>> + bool TraverseTypeLoc(TypeLoc TypeLocNode) {<br>
>> + return TraverseNode(TypeLocNode, &VisitorBase::TraverseTypeLoc);<br>
>> + }<br>
>> +<br>
>> + bool TraverseNestedNameSpecifierLoc(NestedNameSpecifierLoc<br>
>> NNSLocNode) {<br>
>> + return TraverseNode(NNSLocNode,<br>
>> + &VisitorBase::TraverseNestedNameSpecifierLoc);<br>
>> + }<br>
>> +<br>
>> ASTContext::ParentMap *Parents;<br>
>> llvm::SmallVector<ast_type_traits::DynTypedNode, 16> ParentStack;<br>
>><br>
>> @@ -8781,16 +8798,13 @@ namespace {<br>
>><br>
>> ArrayRef<ast_type_traits::DynTypedNode><br>
>> ASTContext::getParents(const ast_type_traits::DynTypedNode &Node) {<br>
>> - assert(Node.getMemoizationData() &&<br>
>> - "Invariant broken: only nodes that support memoization may be "<br>
>> - "used in the parent map.");<br>
>> if (!AllParents) {<br>
>> // We always need to run over the whole translation unit, as<br>
>> // hasAncestor can escape any subtree.<br>
>> AllParents.reset(<br>
>> ParentMapASTVisitor::buildMap(*getTranslationUnitDecl()));<br>
>> }<br>
>> - ParentMap::const_iterator I =<br>
>> AllParents->find(Node.getMemoizationData());<br>
>> + ParentMap::const_iterator I = AllParents->find(Node);<br>
>> if (I == AllParents->end()) {<br>
>> return None;<br>
>> }<br>
>><br>
>> Modified: cfe/trunk/lib/ASTMatchers/ASTMatchFinder.cpp<br>
>> URL:<br>
>> <a href="http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/ASTMatchers/ASTMatchFinder.cpp?rev=250831&r1=250830&r2=250831&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/ASTMatchers/ASTMatchFinder.cpp?rev=250831&r1=250830&r2=250831&view=diff</a><br>
>><br>
>> ==============================================================================<br>
>> --- cfe/trunk/lib/ASTMatchers/ASTMatchFinder.cpp (original)<br>
>> +++ cfe/trunk/lib/ASTMatchers/ASTMatchFinder.cpp Tue Oct 20 10:08:46 2015<br>
>> @@ -621,9 +621,6 @@ private:<br>
>> if (Node.get<TranslationUnitDecl>() ==<br>
>> ActiveASTContext->getTranslationUnitDecl())<br>
>> return false;<br>
>> - assert(Node.getMemoizationData() &&<br>
>> - "Invariant broken: only nodes that support memoization may be<br>
>> "<br>
>> - "used in the parent map.");<br>
>><br>
>> MatchKey Key;<br>
>> Key.MatcherID = Matcher.getID();<br>
>> @@ -867,7 +864,11 @@ bool MatchASTVisitor::TraverseNestedName<br>
>><br>
>> bool MatchASTVisitor::TraverseNestedNameSpecifierLoc(<br>
>> NestedNameSpecifierLoc NNS) {<br>
>> + if (!NNS)<br>
>> + return true;<br>
>> +<br>
>> match(NNS);<br>
>> +<br>
>> // We only match the nested name specifier here (as opposed to<br>
>> traversing it)<br>
>> // because the traversal is already done in the parallel<br>
>> "Loc"-hierarchy.<br>
>> if (NNS.hasQualifier())<br>
>><br>
>> Modified: cfe/trunk/unittests/AST/ASTContextParentMapTest.cpp<br>
>> URL:<br>
>> <a href="http://llvm.org/viewvc/llvm-project/cfe/trunk/unittests/AST/ASTContextParentMapTest.cpp?rev=250831&r1=250830&r2=250831&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/cfe/trunk/unittests/AST/ASTContextParentMapTest.cpp?rev=250831&r1=250830&r2=250831&view=diff</a><br>
>><br>
>> ==============================================================================<br>
>> --- cfe/trunk/unittests/AST/ASTContextParentMapTest.cpp (original)<br>
>> +++ cfe/trunk/unittests/AST/ASTContextParentMapTest.cpp Tue Oct 20<br>
>> 10:08:46 2015<br>
>> @@ -38,6 +38,19 @@ TEST(GetParents, ReturnsParentForStmt) {<br>
>> ifStmt(hasParent(compoundStmt()))));<br>
>> }<br>
>><br>
>> +TEST(GetParents, ReturnsParentForTypeLoc) {<br>
>> + MatchVerifier<TypeLoc> Verifier;<br>
>> + EXPECT_TRUE(<br>
>> + Verifier.match("namespace a { class b {}; } void f(a::b) {}",<br>
>> +<br>
>> typeLoc(hasParent(typeLoc(hasParent(functionDecl()))))));<br>
>> +}<br>
>> +<br>
>> +TEST(GetParents, ReturnsParentForNestedNameSpecifierLoc) {<br>
>> + MatchVerifier<NestedNameSpecifierLoc> Verifier;<br>
>> + EXPECT_TRUE(Verifier.match("namespace a { class b {}; } void f(a::b)<br>
>> {}",<br>
>> +<br>
>> nestedNameSpecifierLoc(hasParent(typeLoc()))));<br>
>> +}<br>
>> +<br>
>> TEST(GetParents, ReturnsParentInsideTemplateInstantiations) {<br>
>> MatchVerifier<Decl> DeclVerifier;<br>
>> EXPECT_TRUE(DeclVerifier.match(<br>
>><br>
>> Modified: cfe/trunk/unittests/ASTMatchers/Dynamic/ParserTest.cpp<br>
>> URL:<br>
>> <a href="http://llvm.org/viewvc/llvm-project/cfe/trunk/unittests/ASTMatchers/Dynamic/ParserTest.cpp?rev=250831&r1=250830&r2=250831&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/cfe/trunk/unittests/ASTMatchers/Dynamic/ParserTest.cpp?rev=250831&r1=250830&r2=250831&view=diff</a><br>
>><br>
>> ==============================================================================<br>
>> --- cfe/trunk/unittests/ASTMatchers/Dynamic/ParserTest.cpp (original)<br>
>> +++ cfe/trunk/unittests/ASTMatchers/Dynamic/ParserTest.cpp Tue Oct 20<br>
>> 10:08:46 2015<br>
>> @@ -318,7 +318,8 @@ TEST(ParserTest, CompletionNamedValues)<br>
>> Comps[1].MatcherDecl);<br>
>><br>
>> EXPECT_EQ("arent(", Comps[2].TypedText);<br>
>> - EXPECT_EQ("Matcher<Decl> hasParent(Matcher<Decl|Stmt>)",<br>
>> + EXPECT_EQ("Matcher<Decl> "<br>
>> +<br>
>> "hasParent(Matcher<NestedNameSpecifierLoc|TypeLoc|Decl|...>)",<br>
>> Comps[2].MatcherDecl);<br>
>> }<br>
>><br>
>><br>
>> Modified: cfe/trunk/unittests/ASTMatchers/Dynamic/RegistryTest.cpp<br>
>> URL:<br>
>> <a href="http://llvm.org/viewvc/llvm-project/cfe/trunk/unittests/ASTMatchers/Dynamic/RegistryTest.cpp?rev=250831&r1=250830&r2=250831&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/cfe/trunk/unittests/ASTMatchers/Dynamic/RegistryTest.cpp?rev=250831&r1=250830&r2=250831&view=diff</a><br>
>><br>
>> ==============================================================================<br>
>> --- cfe/trunk/unittests/ASTMatchers/Dynamic/RegistryTest.cpp (original)<br>
>> +++ cfe/trunk/unittests/ASTMatchers/Dynamic/RegistryTest.cpp Tue Oct 20<br>
>> 10:08:46 2015<br>
>> @@ -447,8 +447,10 @@ TEST_F(RegistryTest, Errors) {<br>
>> TEST_F(RegistryTest, Completion) {<br>
>> CompVector Comps = getCompletions();<br>
>> // Overloaded<br>
>> - EXPECT_TRUE(hasCompletion(<br>
>> - Comps, "hasParent(", "Matcher<Decl|Stmt><br>
>> hasParent(Matcher<Decl|Stmt>)"));<br>
>> + EXPECT_TRUE(hasCompletion(Comps, "hasParent(",<br>
>> +<br>
>> "Matcher<NestedNameSpecifierLoc|TypeLoc|Decl|...> "<br>
>> +<br>
>> "hasParent(Matcher<NestedNameSpecifierLoc|TypeLoc|"<br>
>> + "Decl|...>)"));<br>
>> // Variadic.<br>
>> EXPECT_TRUE(hasCompletion(Comps, "whileStmt(",<br>
>> "Matcher<Stmt><br>
>> whileStmt(Matcher<WhileStmt>...)"));<br>
>> @@ -463,8 +465,10 @@ TEST_F(RegistryTest, Completion) {<br>
>><br>
>> EXPECT_TRUE(hasCompletion(WhileComps, "hasBody(",<br>
>> "Matcher<WhileStmt><br>
>> hasBody(Matcher<Stmt>)"));<br>
>> - EXPECT_TRUE(hasCompletion(WhileComps, "hasParent(",<br>
>> - "Matcher<Stmt><br>
>> hasParent(Matcher<Decl|Stmt>)"));<br>
>> + EXPECT_TRUE(hasCompletion(WhileComps, "hasParent(", "Matcher<Stmt> "<br>
>> +<br>
>> "hasParent(Matcher<"<br>
>> +<br>
>> "NestedNameSpecifierLoc|"<br>
>> +<br>
>> "TypeLoc|Decl|...>)"));<br>
>> EXPECT_TRUE(<br>
>> hasCompletion(WhileComps, "allOf(", "Matcher<T><br>
>> allOf(Matcher<T>...)"));<br>
>><br>
>><br>
>><br>
>> _______________________________________________<br>
>> cfe-commits mailing list<br>
>> <a href="mailto:cfe-commits@lists.llvm.org">cfe-commits@lists.llvm.org</a><br>
>> <a href="http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits" rel="noreferrer" target="_blank">http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits</a><br>
><br>
><br>
</div></div></blockquote></div><br></div>