summaryrefslogtreecommitdiffstats
path: root/lib/Sema/SemaOverload.cpp
diff options
context:
space:
mode:
authorRichard Smith <richard-llvm@metafoo.co.uk>2014-05-17 02:21:47 +0000
committerRichard Smith <richard-llvm@metafoo.co.uk>2014-05-17 02:21:47 +0000
commitac3a79c4d88e7e73d274a73eb11c5fac8ea89c3c (patch)
tree6dde76731f1354b71ac3339808a02b8297605dea /lib/Sema/SemaOverload.cpp
parent44d9eceb47dd8f47e4cefd99e5197ab2e361d9fc (diff)
Switch to a more efficient expression of this check.
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@209055 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/Sema/SemaOverload.cpp')
-rw-r--r--lib/Sema/SemaOverload.cpp44
1 files changed, 24 insertions, 20 deletions
diff --git a/lib/Sema/SemaOverload.cpp b/lib/Sema/SemaOverload.cpp
index bc8eb2cf6a..8d03404e7a 100644
--- a/lib/Sema/SemaOverload.cpp
+++ b/lib/Sema/SemaOverload.cpp
@@ -8309,37 +8309,41 @@ isBetterOverloadCandidate(Sema &S,
// specific_attr_iterator<EnableIfAttr> but going in declaration order,
// instead of reverse order which is how they're stored in the AST.
AttrVec Cand1Attrs;
- AttrVec::iterator Cand1E = Cand1Attrs.end();
if (Cand1.Function->hasAttrs()) {
Cand1Attrs = Cand1.Function->getAttrs();
- Cand1E = std::remove_if(Cand1Attrs.begin(), Cand1Attrs.end(),
- IsNotEnableIfAttr);
- std::reverse(Cand1Attrs.begin(), Cand1E);
+ Cand1Attrs.erase(std::remove_if(Cand1Attrs.begin(), Cand1Attrs.end(),
+ IsNotEnableIfAttr),
+ Cand1Attrs.end());
+ std::reverse(Cand1Attrs.begin(), Cand1Attrs.end());
}
AttrVec Cand2Attrs;
- AttrVec::iterator Cand2E = Cand2Attrs.end();
if (Cand2.Function->hasAttrs()) {
Cand2Attrs = Cand2.Function->getAttrs();
- Cand2E = std::remove_if(Cand2Attrs.begin(), Cand2Attrs.end(),
- IsNotEnableIfAttr);
- std::reverse(Cand2Attrs.begin(), Cand2E);
- }
- for (AttrVec::iterator
- Cand1I = Cand1Attrs.begin(), Cand2I = Cand2Attrs.begin();
- Cand1I != Cand1E || Cand2I != Cand2E; ++Cand1I, ++Cand2I) {
- if (Cand1I == Cand1E)
- return false;
- if (Cand2I == Cand2E)
- return true;
+ Cand2Attrs.erase(std::remove_if(Cand2Attrs.begin(), Cand2Attrs.end(),
+ IsNotEnableIfAttr),
+ Cand2Attrs.end());
+ std::reverse(Cand2Attrs.begin(), Cand2Attrs.end());
+ }
+
+ // Candidate 1 is better if it has strictly more attributes and
+ // the common sequence is identical.
+ if (Cand1Attrs.size() <= Cand2Attrs.size())
+ return false;
+
+ auto Cand1I = Cand1Attrs.begin();
+ for (auto &Cand2A : Cand2Attrs) {
+ auto &Cand1A = *Cand1I++;
llvm::FoldingSetNodeID Cand1ID, Cand2ID;
- cast<EnableIfAttr>(*Cand1I)->getCond()->Profile(Cand1ID,
- S.getASTContext(), true);
- cast<EnableIfAttr>(*Cand2I)->getCond()->Profile(Cand2ID,
- S.getASTContext(), true);
+ cast<EnableIfAttr>(Cand1A)->getCond()->Profile(Cand1ID,
+ S.getASTContext(), true);
+ cast<EnableIfAttr>(Cand2A)->getCond()->Profile(Cand2ID,
+ S.getASTContext(), true);
if (Cand1ID != Cand2ID)
return false;
}
+
+ return true;
}
return false;