r318205 - [refactor][selection] canonicalize member expr callee to the full
Alex Lorenz via cfe-commits
cfe-commits at lists.llvm.org
Tue Nov 14 14:06:55 PST 2017
Author: arphaman
Date: Tue Nov 14 14:06:55 2017
New Revision: 318205
URL: http://llvm.org/viewvc/llvm-project?rev=318205&view=rev
Log:
[refactor][selection] canonicalize member expr callee to the full
member call expression
We would like to extract the full call when just the callee is selected.
Modified:
cfe/trunk/lib/Tooling/Refactoring/ASTSelection.cpp
cfe/trunk/unittests/Tooling/ASTSelectionTest.cpp
Modified: cfe/trunk/lib/Tooling/Refactoring/ASTSelection.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Tooling/Refactoring/ASTSelection.cpp?rev=318205&r1=318204&r2=318205&view=diff
==============================================================================
--- cfe/trunk/lib/Tooling/Refactoring/ASTSelection.cpp (original)
+++ cfe/trunk/lib/Tooling/Refactoring/ASTSelection.cpp Tue Nov 14 14:06:55 2017
@@ -115,6 +115,11 @@ public:
return true;
if (auto *Opaque = dyn_cast<OpaqueValueExpr>(S))
return TraverseOpaqueValueExpr(Opaque);
+ // Avoid selecting implicit 'this' expressions.
+ if (auto *TE = dyn_cast<CXXThisExpr>(S)) {
+ if (TE->isImplicit())
+ return true;
+ }
// FIXME (Alex Lorenz): Improve handling for macro locations.
SourceSelectionKind SelectionKind =
selectionKindFor(CharSourceRange::getTokenRange(S->getSourceRange()));
@@ -268,9 +273,15 @@ void SelectedNodeWithParents::canonicali
// ~~~~~~ ~~~~~~~
if (isa<StringLiteral>(S) && isa<ObjCStringLiteral>(Parent))
Node = Parents.pop_back_val();
+ // The entire call should be selected when just the member expression
+ // that refers to the method is selected.
+ // f.call(args) becomes f.call(args)
+ // ~~~~ ~~~~~~~~~~~~
+ else if (isa<MemberExpr>(S) && isa<CXXMemberCallExpr>(Parent) &&
+ cast<CXXMemberCallExpr>(Parent)->getCallee() == S)
+ Node = Parents.pop_back_val();
// FIXME: Syntactic form -> Entire pseudo-object expr.
// FIXME: Callee -> Call.
- // FIXME: Callee member expr -> Call.
}
/// Finds the set of bottom-most selected AST nodes that are in the selection
Modified: cfe/trunk/unittests/Tooling/ASTSelectionTest.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/unittests/Tooling/ASTSelectionTest.cpp?rev=318205&r1=318204&r2=318205&view=diff
==============================================================================
--- cfe/trunk/unittests/Tooling/ASTSelectionTest.cpp (original)
+++ cfe/trunk/unittests/Tooling/ASTSelectionTest.cpp Tue Nov 14 14:06:55 2017
@@ -1004,4 +1004,56 @@ void foo() {
SelectionFinderVisitor::Lang_OBJC);
}
+TEST(ASTSelectionFinder, CanonicalizeMemberCalleeToCall) {
+ StringRef Source = R"(
+class AClass { public:
+ void method();
+ int afield;
+ void selectWholeCallWhenJustMethodSelected(int &i) {
+ method();
+ }
+};
+void selectWholeCallWhenJustMethodSelected() {
+ AClass a;
+ a.method();
+}
+void dontSelectArgument(AClass &a) {
+ a.selectWholeCallWhenJustMethodSelected(a.afield);
+}
+ )";
+ // Just 'method' with implicit 'this':
+ findSelectedASTNodesWithRange(
+ Source, {6, 5}, FileRange{{6, 5}, {6, 11}},
+ [](SourceRange SelectionRange, Optional<SelectedASTNode> Node) {
+ EXPECT_TRUE(Node);
+ Optional<CodeRangeASTSelection> SelectedCode =
+ CodeRangeASTSelection::create(SelectionRange, std::move(*Node));
+ EXPECT_TRUE(SelectedCode);
+ EXPECT_EQ(SelectedCode->size(), 1u);
+ EXPECT_TRUE(isa<CXXMemberCallExpr>((*SelectedCode)[0]));
+ });
+ // Just 'method':
+ findSelectedASTNodesWithRange(
+ Source, {11, 5}, FileRange{{11, 5}, {11, 11}},
+ [](SourceRange SelectionRange, Optional<SelectedASTNode> Node) {
+ EXPECT_TRUE(Node);
+ Optional<CodeRangeASTSelection> SelectedCode =
+ CodeRangeASTSelection::create(SelectionRange, std::move(*Node));
+ EXPECT_TRUE(SelectedCode);
+ EXPECT_EQ(SelectedCode->size(), 1u);
+ EXPECT_TRUE(isa<CXXMemberCallExpr>((*SelectedCode)[0]));
+ });
+ // Just 'afield', which should not select the call.
+ findSelectedASTNodesWithRange(
+ Source, {14, 5}, FileRange{{14, 45}, {14, 51}},
+ [](SourceRange SelectionRange, Optional<SelectedASTNode> Node) {
+ EXPECT_TRUE(Node);
+ Optional<CodeRangeASTSelection> SelectedCode =
+ CodeRangeASTSelection::create(SelectionRange, std::move(*Node));
+ EXPECT_TRUE(SelectedCode);
+ EXPECT_EQ(SelectedCode->size(), 1u);
+ EXPECT_FALSE(isa<CXXMemberCallExpr>((*SelectedCode)[0]));
+ });
+}
+
} // end anonymous namespace
More information about the cfe-commits
mailing list