summaryrefslogtreecommitdiffstats
path: root/clang/lib
diff options
context:
space:
mode:
authorSamuel Benzaquen <sbenza@google.com>2014-10-06 13:14:30 +0000
committerSamuel Benzaquen <sbenza@google.com>2014-10-06 13:14:30 +0000
commita117002d93b1f0e9488a68d5d3b540ca795bc9e5 (patch)
tree71f19d127eb772033bf647f2b86152bac7d43702 /clang/lib
parentfaef77480d0ff27dca79b4a60f6863bf97d30854 (diff)
downloadbcm5719-llvm-a117002d93b1f0e9488a68d5d3b540ca795bc9e5.tar.gz
bcm5719-llvm-a117002d93b1f0e9488a68d5d3b540ca795bc9e5.zip
Fix bug in DynTypedMatcher::constructVariadic() that would cause false negatives.
Summary: DynTypedMatcher::constructVariadic() where the restrict kind of the different matchers are not related causes the matcher to have a "None" restrict kind. This causes false negatives for anyOf and eachOf. Change the logic to get a common ancestor if there is one. Also added regression tests that fail without the fix. Reviewers: klimek Subscribers: klimek, cfe-commits Differential Revision: http://reviews.llvm.org/D5580 llvm-svn: 219118
Diffstat (limited to 'clang/lib')
-rw-r--r--clang/lib/AST/ASTTypeTraits.cpp16
-rw-r--r--clang/lib/ASTMatchers/ASTMatchersInternal.cpp28
2 files changed, 20 insertions, 24 deletions
diff --git a/clang/lib/AST/ASTTypeTraits.cpp b/clang/lib/AST/ASTTypeTraits.cpp
index 56915b96406..ec0671ceb1b 100644
--- a/clang/lib/AST/ASTTypeTraits.cpp
+++ b/clang/lib/AST/ASTTypeTraits.cpp
@@ -62,6 +62,22 @@ bool ASTNodeKind::isBaseOf(NodeKindId Base, NodeKindId Derived,
StringRef ASTNodeKind::asStringRef() const { return AllKindInfo[KindId].Name; }
+ASTNodeKind ASTNodeKind::getMostDerivedType(ASTNodeKind Kind1,
+ ASTNodeKind Kind2) {
+ if (Kind1.isBaseOf(Kind2)) return Kind2;
+ if (Kind2.isBaseOf(Kind1)) return Kind1;
+ return ASTNodeKind();
+}
+
+ASTNodeKind ASTNodeKind::getMostDerivedCommonAncestor(ASTNodeKind Kind1,
+ ASTNodeKind Kind2) {
+ NodeKindId Parent = Kind1.KindId;
+ while (!isBaseOf(Parent, Kind2.KindId, nullptr) && Parent != NKI_None) {
+ Parent = AllKindInfo[Parent].ParentId;
+ }
+ return ASTNodeKind(Parent);
+}
+
ASTNodeKind ASTNodeKind::getFromNode(const Decl &D) {
switch (D.getKind()) {
#define DECL(DERIVED, BASE) \
diff --git a/clang/lib/ASTMatchers/ASTMatchersInternal.cpp b/clang/lib/ASTMatchers/ASTMatchersInternal.cpp
index 4cff381f3f4..ec60f0d9498 100644
--- a/clang/lib/ASTMatchers/ASTMatchersInternal.cpp
+++ b/clang/lib/ASTMatchers/ASTMatchersInternal.cpp
@@ -64,28 +64,6 @@ class IdDynMatcher : public DynMatcherInterface {
const IntrusiveRefCntPtr<DynMatcherInterface> InnerMatcher;
};
-/// \brief Return the most derived type between \p Kind1 and \p Kind2.
-///
-/// Return the null type if they are not related.
-ast_type_traits::ASTNodeKind getMostDerivedType(
- const ast_type_traits::ASTNodeKind Kind1,
- const ast_type_traits::ASTNodeKind Kind2) {
- if (Kind1.isBaseOf(Kind2)) return Kind2;
- if (Kind2.isBaseOf(Kind1)) return Kind1;
- return ast_type_traits::ASTNodeKind();
-}
-
-/// \brief Return the least derived type between \p Kind1 and \p Kind2.
-///
-/// Return the null type if they are not related.
-static ast_type_traits::ASTNodeKind getLeastDerivedType(
- const ast_type_traits::ASTNodeKind Kind1,
- const ast_type_traits::ASTNodeKind Kind2) {
- if (Kind1.isBaseOf(Kind2)) return Kind1;
- if (Kind2.isBaseOf(Kind1)) return Kind2;
- return ast_type_traits::ASTNodeKind();
-}
-
} // namespace
DynTypedMatcher DynTypedMatcher::constructVariadic(
@@ -98,7 +76,8 @@ DynTypedMatcher DynTypedMatcher::constructVariadic(
assert(Result.SupportedKind.isSame(M.SupportedKind) &&
"SupportedKind must match!");
Result.RestrictKind =
- getLeastDerivedType(Result.RestrictKind, M.RestrictKind);
+ ast_type_traits::ASTNodeKind::getMostDerivedCommonAncestor(
+ Result.RestrictKind, M.RestrictKind);
}
Result.Implementation = new VariadicMatcher(Func, std::move(InnerMatchers));
return Result;
@@ -108,7 +87,8 @@ DynTypedMatcher DynTypedMatcher::dynCastTo(
const ast_type_traits::ASTNodeKind Kind) const {
auto Copy = *this;
Copy.SupportedKind = Kind;
- Copy.RestrictKind = getMostDerivedType(Kind, RestrictKind);
+ Copy.RestrictKind =
+ ast_type_traits::ASTNodeKind::getMostDerivedType(Kind, RestrictKind);
return Copy;
}
OpenPOWER on IntegriCloud