]> granicus.if.org Git - clang/commitdiff
Convert SemaCXXScopeSpec.cpp to pass a callback object to CorrectTypo,
authorKaelyn Uhrain <rikka@google.com>
Thu, 12 Jan 2012 22:32:39 +0000 (22:32 +0000)
committerKaelyn Uhrain <rikka@google.com>
Thu, 12 Jan 2012 22:32:39 +0000 (22:32 +0000)
improvng the typo correction results in certain situations.

git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@148052 91177308-0d34-0410-b5e6-96231b3b80d8

lib/Sema/SemaCXXScopeSpec.cpp
test/SemaCXX/typo-correction.cpp

index 93f83256b018daa55a80b00e2e1a43d585ca6168..31e33dda08ade58801722838b0ccf5d45540c508 100644 (file)
@@ -363,6 +363,25 @@ bool Sema::isNonTypeNestedNameSpecifier(Scope *S, CXXScopeSpec &SS,
   return false;
 }
 
+namespace {
+
+// Callback to only accept typo corrections that can be a valid C++ member
+// intializer: either a non-static field member or a base class.
+class NestedNameSpecifierValidatorCCC : public CorrectionCandidateCallback {
+ public:
+  explicit NestedNameSpecifierValidatorCCC(Sema &SRef)
+      : SRef(SRef) {}
+
+  virtual bool ValidateCandidate(const TypoCorrection &candidate) {
+    return SRef.isAcceptableNestedNameSpecifier(candidate.getCorrectionDecl());
+  }
+
+ private:
+  Sema &SRef;
+};
+
+}
+
 /// \brief Build a new nested-name-specifier for "identifier::", as described
 /// by ActOnCXXNestedNameSpecifier.
 ///
@@ -478,12 +497,12 @@ bool Sema::BuildCXXNestedNameSpecifier(Scope *S,
     // We haven't found anything, and we're not recovering from a
     // different kind of error, so look for typos.
     DeclarationName Name = Found.getLookupName();
+    NestedNameSpecifierValidatorCCC Validator(*this);
     TypoCorrection Corrected;
     Found.clear();
     if ((Corrected = CorrectTypo(Found.getLookupNameInfo(),
-                                 Found.getLookupKind(), S, &SS, LookupCtx,
-                                 EnteringContext, CTC_NoKeywords)) &&
-        isAcceptableNestedNameSpecifier(Corrected.getCorrectionDecl())) {
+                                 Found.getLookupKind(), S, &SS, &Validator,
+                                 LookupCtx, EnteringContext))) {
       std::string CorrectedStr(Corrected.getAsString(getLangOptions()));
       std::string CorrectedQuotedStr(Corrected.getQuoted(getLangOptions()));
       if (LookupCtx)
index 9187c1bf1293fe520a67192e0ed0d24cfd942b6f..a4cbbb85e6b396e3834da76e24f44a8bdb093b2b 100644 (file)
@@ -59,3 +59,11 @@ struct st {
   double FieldA; // expected-note{{'FieldA' declared here}}
 };
 st var = { .fielda = 0.0 }; // expected-error{{field designator 'fielda' does not refer to any field in type 'st'; did you mean 'FieldA'?}}
+
+// Test the improvement from passing a  callback object to CorrectTypo in
+// Sema::BuildCXXNestedNameSpecifier.
+typedef char* another_str;
+namespace AnotherStd { // expected-note{{'AnotherStd' declared here}}
+  class string {};
+}
+another_std::string str; // expected-error{{use of undeclared identifier 'another_std'; did you mean 'AnotherStd'?}}