aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorKaelyn Uhrain <rikka@google.com>2011-09-14 19:37:32 +0000
committerKaelyn Uhrain <rikka@google.com>2011-09-14 19:37:32 +0000
commit7fbe2f78d7c0ba4106e281265f512c53aa77276e (patch)
tree103ca044fa8d7a104bfe05b63ff53a1f135f8eb0
parente9d80bbc1d119cc0fc8aa3a0f91866264b0eb58f (diff)
downloadllvm-7fbe2f78d7c0ba4106e281265f512c53aa77276e.zip
llvm-7fbe2f78d7c0ba4106e281265f512c53aa77276e.tar.gz
llvm-7fbe2f78d7c0ba4106e281265f512c53aa77276e.tar.bz2
Plug an abstraction leak and fix a crasher in DiagnoseInvalidRedeclaration
llvm-svn: 139718
-rw-r--r--clang/include/clang/Sema/TypoCorrection.h4
-rw-r--r--clang/lib/Sema/SemaDecl.cpp9
-rw-r--r--clang/test/SemaCXX/function-redecl.cpp9
3 files changed, 19 insertions, 3 deletions
diff --git a/clang/include/clang/Sema/TypoCorrection.h b/clang/include/clang/Sema/TypoCorrection.h
index 480a71a..9537c30 100644
--- a/clang/include/clang/Sema/TypoCorrection.h
+++ b/clang/include/clang/Sema/TypoCorrection.h
@@ -118,7 +118,9 @@ public:
}
typedef llvm::SmallVector<NamedDecl*, 1>::iterator decl_iterator;
- decl_iterator begin() { return CorrectionDecls.begin(); }
+ decl_iterator begin() {
+ return isKeyword() ? CorrectionDecls.end() : CorrectionDecls.begin();
+ }
decl_iterator end() { return CorrectionDecls.end(); }
private:
diff --git a/clang/lib/Sema/SemaDecl.cpp b/clang/lib/Sema/SemaDecl.cpp
index 96531d4..abc3cf1 100644
--- a/clang/lib/Sema/SemaDecl.cpp
+++ b/clang/lib/Sema/SemaDecl.cpp
@@ -4284,8 +4284,6 @@ static void DiagnoseInvalidRedeclaration(Sema &S, FunctionDecl *NewFD,
} else if ((Correction = S.CorrectTypo(Prev.getLookupNameInfo(),
Prev.getLookupKind(), 0, 0, DC)) &&
Correction.getCorrection() != Name) {
- DiagMsg = isFriendDecl ? diag::err_no_matching_local_friend_suggest
- : diag::err_member_def_does_not_match_suggest;
for (TypoCorrection::decl_iterator CDecl = Correction.begin(),
CDeclEnd = Correction.end();
CDecl != CDeclEnd; ++CDecl) {
@@ -4299,8 +4297,15 @@ static void DiagnoseInvalidRedeclaration(Sema &S, FunctionDecl *NewFD,
NearMatches.push_back(std::make_pair(FD, ParamNum));
}
}
+ if (!NearMatches.empty())
+ DiagMsg = isFriendDecl ? diag::err_no_matching_local_friend_suggest
+ : diag::err_member_def_does_not_match_suggest;
}
+ // Ignore the correction if it didn't yield any close FunctionDecl matches
+ if (Correction && NearMatches.empty())
+ Correction = TypoCorrection();
+
if (Correction)
S.Diag(NewFD->getLocation(), DiagMsg)
<< Name << DC << Correction.getQuoted(S.getLangOptions())
diff --git a/clang/test/SemaCXX/function-redecl.cpp b/clang/test/SemaCXX/function-redecl.cpp
index b31e42e..2bc04a6 100644
--- a/clang/test/SemaCXX/function-redecl.cpp
+++ b/clang/test/SemaCXX/function-redecl.cpp
@@ -70,3 +70,12 @@ using test1::Foo;
void Bar::f(Foo::Inner foo) { // expected-error {{out-of-line definition of 'f' does not match any declaration in 'Bar'}}
(void)foo;
}
+
+class Crash {
+ public:
+ void GetCart(int count) const;
+};
+// This out-of-line definition was fine...
+void Crash::cart(int count) const {} // expected-error {{out-of-line definition of 'cart' does not match any declaration in 'Crash'}}
+// ...while this one crashed clang
+void Crash::chart(int count) const {} // expected-error {{out-of-line definition of 'chart' does not match any declaration in 'Crash'}}