2019-02-06 17:08:26 +08:00
|
|
|
//===-- SelectionTests.cpp - ----------------------------------------------===//
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
//
|
|
|
|
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
|
|
|
|
// See https://llvm.org/LICENSE.txt for license information.
|
|
|
|
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
|
|
|
|
//
|
|
|
|
//===----------------------------------------------------------------------===//
|
|
|
|
#include "Annotations.h"
|
|
|
|
#include "Selection.h"
|
|
|
|
#include "SourceCode.h"
|
|
|
|
#include "TestTU.h"
|
2020-05-11 17:02:34 +08:00
|
|
|
#include "support/TestTracer.h"
|
[clangd] SelectionTree treats TranslationUnitDecl (mostly) consistently with other containers.
Summary:
Previously TranslationUnitDecl would never be selected.
This means root() is never null, and returns a reference.
commonAncestor() is in principle never null also, but returning TUDecl
here requires tweaks to be careful not to traverse it (this was already
possible when selecting multiple top-level decls, and there are associated bugs!)
Instead, never allow commonAncestor() to return TUDecl, return null instead.
Reviewers: hokein
Subscribers: ilya-biryukov, MaskRay, jkorous, arphaman, kadircet, cfe-commits
Tags: #clang
Differential Revision: https://reviews.llvm.org/D65101
llvm-svn: 366893
2019-07-24 20:14:56 +08:00
|
|
|
#include "clang/AST/Decl.h"
|
|
|
|
#include "llvm/Support/Casting.h"
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
#include "gmock/gmock.h"
|
|
|
|
#include "gtest/gtest.h"
|
|
|
|
|
|
|
|
namespace clang {
|
|
|
|
namespace clangd {
|
|
|
|
namespace {
|
2020-12-07 17:52:04 +08:00
|
|
|
using ::testing::ElementsAreArray;
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
using ::testing::UnorderedElementsAreArray;
|
|
|
|
|
2020-02-24 03:03:00 +08:00
|
|
|
// Create a selection tree corresponding to a point or pair of points.
|
|
|
|
// This uses the precisely-defined createRight semantics. The fuzzier
|
|
|
|
// createEach is tested separately.
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
SelectionTree makeSelectionTree(const StringRef MarkedCode, ParsedAST &AST) {
|
|
|
|
Annotations Test(MarkedCode);
|
|
|
|
switch (Test.points().size()) {
|
2020-02-24 03:03:00 +08:00
|
|
|
case 1: { // Point selection.
|
|
|
|
unsigned Offset = cantFail(positionToOffset(Test.code(), Test.point()));
|
|
|
|
return SelectionTree::createRight(AST.getASTContext(), AST.getTokens(),
|
|
|
|
Offset, Offset);
|
|
|
|
}
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
case 2: // Range selection.
|
2020-02-24 03:03:00 +08:00
|
|
|
return SelectionTree::createRight(
|
[clangd] Ignore semicolons, whitespace, and comments in SelectionTree.
Summary:
Whitespace and comments are a clear bugfix: selecting some
comments/space near a statement doesn't mean you're selecting the
surrounding block.
Semicolons are less obvious, but for similar reasons: these tokens
aren't actually claimed by any AST node (usually), so an AST-based model
like SelectionTree shouldn't take them into account.
Callers may still sometimes care about semis of course:
- when the selection is an expr with a non-expr parent, selection of
the semicolon indicates intent to select the statement.
- when a statement with a trailing semi is selected, we need to know
its range to ensure it can be removed.
SelectionTree may or may not play a role here, but these are separate questions
from its core function of describing which AST nodes were selected.
The mechanism here is the TokenBuffer from syntax-trees. We use it in a
fairly low-level way (just to get boundaries of raw spelled tokens). The
actual mapping of AST nodes to coordinates continues to use the (fairly
mature) SourceLocation based logic. TokenBuffer/Syntax trees
don't currently offer an alternative to getFileRange(), I think.
Reviewers: SureYeaah, kadircet
Subscribers: MaskRay, jkorous, arphaman, cfe-commits, ilya-biryukov
Tags: #clang
Differential Revision: https://reviews.llvm.org/D65486
llvm-svn: 367453
2019-08-01 01:52:40 +08:00
|
|
|
AST.getASTContext(), AST.getTokens(),
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
cantFail(positionToOffset(Test.code(), Test.points()[0])),
|
|
|
|
cantFail(positionToOffset(Test.code(), Test.points()[1])));
|
|
|
|
default:
|
|
|
|
ADD_FAILURE() << "Expected 1-2 points for selection.\n" << MarkedCode;
|
2020-02-24 03:03:00 +08:00
|
|
|
return SelectionTree::createRight(AST.getASTContext(), AST.getTokens(), 0u,
|
|
|
|
0u);
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
Range nodeRange(const SelectionTree::Node *N, ParsedAST &AST) {
|
|
|
|
if (!N)
|
|
|
|
return Range{};
|
2019-07-19 19:41:02 +08:00
|
|
|
const SourceManager &SM = AST.getSourceManager();
|
2019-12-05 07:09:35 +08:00
|
|
|
const LangOptions &LangOpts = AST.getLangOpts();
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
StringRef Buffer = SM.getBufferData(SM.getMainFileID());
|
[clangd] SelectionTree treats TranslationUnitDecl (mostly) consistently with other containers.
Summary:
Previously TranslationUnitDecl would never be selected.
This means root() is never null, and returns a reference.
commonAncestor() is in principle never null also, but returning TUDecl
here requires tweaks to be careful not to traverse it (this was already
possible when selecting multiple top-level decls, and there are associated bugs!)
Instead, never allow commonAncestor() to return TUDecl, return null instead.
Reviewers: hokein
Subscribers: ilya-biryukov, MaskRay, jkorous, arphaman, kadircet, cfe-commits
Tags: #clang
Differential Revision: https://reviews.llvm.org/D65101
llvm-svn: 366893
2019-07-24 20:14:56 +08:00
|
|
|
if (llvm::isa_and_nonnull<TranslationUnitDecl>(N->ASTNode.get<Decl>()))
|
|
|
|
return Range{Position{}, offsetToPosition(Buffer, Buffer.size())};
|
2019-07-19 19:41:02 +08:00
|
|
|
auto FileRange =
|
|
|
|
toHalfOpenFileRange(SM, LangOpts, N->ASTNode.getSourceRange());
|
|
|
|
assert(FileRange && "We should be able to get the File Range");
|
|
|
|
return Range{
|
|
|
|
offsetToPosition(Buffer, SM.getFileOffset(FileRange->getBegin())),
|
|
|
|
offsetToPosition(Buffer, SM.getFileOffset(FileRange->getEnd()))};
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
std::string nodeKind(const SelectionTree::Node *N) {
|
2019-07-24 17:39:11 +08:00
|
|
|
return N ? N->kind() : "<null>";
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
std::vector<const SelectionTree::Node *> allNodes(const SelectionTree &T) {
|
[clangd] SelectionTree treats TranslationUnitDecl (mostly) consistently with other containers.
Summary:
Previously TranslationUnitDecl would never be selected.
This means root() is never null, and returns a reference.
commonAncestor() is in principle never null also, but returning TUDecl
here requires tweaks to be careful not to traverse it (this was already
possible when selecting multiple top-level decls, and there are associated bugs!)
Instead, never allow commonAncestor() to return TUDecl, return null instead.
Reviewers: hokein
Subscribers: ilya-biryukov, MaskRay, jkorous, arphaman, kadircet, cfe-commits
Tags: #clang
Differential Revision: https://reviews.llvm.org/D65101
llvm-svn: 366893
2019-07-24 20:14:56 +08:00
|
|
|
std::vector<const SelectionTree::Node *> Result = {&T.root()};
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
for (unsigned I = 0; I < Result.size(); ++I) {
|
|
|
|
const SelectionTree::Node *N = Result[I];
|
|
|
|
Result.insert(Result.end(), N->Children.begin(), N->Children.end());
|
|
|
|
}
|
|
|
|
return Result;
|
|
|
|
}
|
|
|
|
|
|
|
|
// Returns true if Common is a descendent of Root.
|
|
|
|
// Verifies nothing is selected above Common.
|
[clangd] SelectionTree treats TranslationUnitDecl (mostly) consistently with other containers.
Summary:
Previously TranslationUnitDecl would never be selected.
This means root() is never null, and returns a reference.
commonAncestor() is in principle never null also, but returning TUDecl
here requires tweaks to be careful not to traverse it (this was already
possible when selecting multiple top-level decls, and there are associated bugs!)
Instead, never allow commonAncestor() to return TUDecl, return null instead.
Reviewers: hokein
Subscribers: ilya-biryukov, MaskRay, jkorous, arphaman, kadircet, cfe-commits
Tags: #clang
Differential Revision: https://reviews.llvm.org/D65101
llvm-svn: 366893
2019-07-24 20:14:56 +08:00
|
|
|
bool verifyCommonAncestor(const SelectionTree::Node &Root,
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
const SelectionTree::Node *Common,
|
|
|
|
StringRef MarkedCode) {
|
[clangd] SelectionTree treats TranslationUnitDecl (mostly) consistently with other containers.
Summary:
Previously TranslationUnitDecl would never be selected.
This means root() is never null, and returns a reference.
commonAncestor() is in principle never null also, but returning TUDecl
here requires tweaks to be careful not to traverse it (this was already
possible when selecting multiple top-level decls, and there are associated bugs!)
Instead, never allow commonAncestor() to return TUDecl, return null instead.
Reviewers: hokein
Subscribers: ilya-biryukov, MaskRay, jkorous, arphaman, kadircet, cfe-commits
Tags: #clang
Differential Revision: https://reviews.llvm.org/D65101
llvm-svn: 366893
2019-07-24 20:14:56 +08:00
|
|
|
if (&Root == Common)
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
return true;
|
[clangd] SelectionTree treats TranslationUnitDecl (mostly) consistently with other containers.
Summary:
Previously TranslationUnitDecl would never be selected.
This means root() is never null, and returns a reference.
commonAncestor() is in principle never null also, but returning TUDecl
here requires tweaks to be careful not to traverse it (this was already
possible when selecting multiple top-level decls, and there are associated bugs!)
Instead, never allow commonAncestor() to return TUDecl, return null instead.
Reviewers: hokein
Subscribers: ilya-biryukov, MaskRay, jkorous, arphaman, kadircet, cfe-commits
Tags: #clang
Differential Revision: https://reviews.llvm.org/D65101
llvm-svn: 366893
2019-07-24 20:14:56 +08:00
|
|
|
if (Root.Selected)
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
ADD_FAILURE() << "Selected nodes outside common ancestor\n" << MarkedCode;
|
|
|
|
bool Seen = false;
|
[clangd] SelectionTree treats TranslationUnitDecl (mostly) consistently with other containers.
Summary:
Previously TranslationUnitDecl would never be selected.
This means root() is never null, and returns a reference.
commonAncestor() is in principle never null also, but returning TUDecl
here requires tweaks to be careful not to traverse it (this was already
possible when selecting multiple top-level decls, and there are associated bugs!)
Instead, never allow commonAncestor() to return TUDecl, return null instead.
Reviewers: hokein
Subscribers: ilya-biryukov, MaskRay, jkorous, arphaman, kadircet, cfe-commits
Tags: #clang
Differential Revision: https://reviews.llvm.org/D65101
llvm-svn: 366893
2019-07-24 20:14:56 +08:00
|
|
|
for (const SelectionTree::Node *Child : Root.Children)
|
|
|
|
if (verifyCommonAncestor(*Child, Common, MarkedCode)) {
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
if (Seen)
|
|
|
|
ADD_FAILURE() << "Saw common ancestor twice\n" << MarkedCode;
|
|
|
|
Seen = true;
|
|
|
|
}
|
|
|
|
return Seen;
|
|
|
|
}
|
|
|
|
|
|
|
|
TEST(SelectionTest, CommonAncestor) {
|
|
|
|
struct Case {
|
|
|
|
// Selection is between ^marks^.
|
|
|
|
// common ancestor marked with a [[range]].
|
|
|
|
const char *Code;
|
|
|
|
const char *CommonAncestorKind;
|
|
|
|
};
|
|
|
|
Case Cases[] = {
|
2019-06-25 17:36:09 +08:00
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
template <typename T>
|
|
|
|
int x = [[T::^U::]]ccc();
|
|
|
|
)cpp",
|
|
|
|
"NestedNameSpecifierLoc",
|
|
|
|
},
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
struct AAA { struct BBB { static int ccc(); };};
|
|
|
|
int x = AAA::[[B^B^B]]::ccc();
|
|
|
|
)cpp",
|
2019-07-24 17:39:11 +08:00
|
|
|
"RecordTypeLoc",
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
},
|
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
struct AAA { struct BBB { static int ccc(); };};
|
|
|
|
int x = AAA::[[B^BB^]]::ccc();
|
|
|
|
)cpp",
|
2019-07-24 17:39:11 +08:00
|
|
|
"RecordTypeLoc",
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
},
|
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
struct AAA { struct BBB { static int ccc(); };};
|
|
|
|
int x = [[AAA::BBB::c^c^c]]();
|
|
|
|
)cpp",
|
|
|
|
"DeclRefExpr",
|
|
|
|
},
|
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
struct AAA { struct BBB { static int ccc(); };};
|
|
|
|
int x = [[AAA::BBB::cc^c(^)]];
|
|
|
|
)cpp",
|
|
|
|
"CallExpr",
|
|
|
|
},
|
|
|
|
|
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
void foo() { [[if (1^11) { return; } else {^ }]] }
|
|
|
|
)cpp",
|
|
|
|
"IfStmt",
|
|
|
|
},
|
2019-12-03 23:59:52 +08:00
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
int x(int);
|
|
|
|
#define M(foo) x(foo)
|
|
|
|
int a = 42;
|
|
|
|
int b = M([[^a]]);
|
|
|
|
)cpp",
|
|
|
|
"DeclRefExpr",
|
|
|
|
},
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
void foo();
|
|
|
|
#define CALL_FUNCTION(X) X()
|
|
|
|
void bar() { CALL_FUNCTION([[f^o^o]]); }
|
|
|
|
)cpp",
|
|
|
|
"DeclRefExpr",
|
|
|
|
},
|
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
void foo();
|
|
|
|
#define CALL_FUNCTION(X) X()
|
2019-07-19 19:41:02 +08:00
|
|
|
void bar() { [[CALL_FUNC^TION(fo^o)]]; }
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
)cpp",
|
2019-07-19 19:41:02 +08:00
|
|
|
"CallExpr",
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
},
|
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
void foo();
|
|
|
|
#define CALL_FUNCTION(X) X()
|
2019-07-19 19:41:02 +08:00
|
|
|
void bar() { [[C^ALL_FUNC^TION(foo)]]; }
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
)cpp",
|
2019-07-19 19:41:02 +08:00
|
|
|
"CallExpr",
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
},
|
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
void foo();
|
2020-07-17 18:03:24 +08:00
|
|
|
#^define CALL_FUNCTION(X) X(^)
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
void bar() { CALL_FUNCTION(foo); }
|
|
|
|
)cpp",
|
|
|
|
nullptr,
|
|
|
|
},
|
2020-07-17 18:03:24 +08:00
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
void foo();
|
|
|
|
#define CALL_FUNCTION(X) X()
|
|
|
|
void bar() { CALL_FUNCTION(foo^)^; }
|
|
|
|
)cpp",
|
|
|
|
nullptr,
|
|
|
|
},
|
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
namespace ns {
|
|
|
|
#if 0
|
|
|
|
void fo^o() {}
|
|
|
|
#endif
|
|
|
|
}
|
|
|
|
)cpp",
|
|
|
|
nullptr,
|
|
|
|
},
|
2019-06-27 19:17:13 +08:00
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
struct S { S(const char*); };
|
|
|
|
S [[s ^= "foo"]];
|
|
|
|
)cpp",
|
|
|
|
"CXXConstructExpr",
|
|
|
|
},
|
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
struct S { S(const char*); };
|
|
|
|
[[S ^s = "foo"]];
|
|
|
|
)cpp",
|
|
|
|
"VarDecl",
|
|
|
|
},
|
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
[[^void]] (*S)(int) = nullptr;
|
|
|
|
)cpp",
|
2019-07-24 17:39:11 +08:00
|
|
|
"BuiltinTypeLoc",
|
2019-06-27 19:17:13 +08:00
|
|
|
},
|
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
[[void (*S)^(int)]] = nullptr;
|
|
|
|
)cpp",
|
2019-07-24 17:39:11 +08:00
|
|
|
"FunctionProtoTypeLoc",
|
2019-06-27 19:17:13 +08:00
|
|
|
},
|
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
[[void (^*S)(int)]] = nullptr;
|
|
|
|
)cpp",
|
2019-07-24 17:39:11 +08:00
|
|
|
"FunctionProtoTypeLoc",
|
2019-06-27 19:17:13 +08:00
|
|
|
},
|
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
[[void (*^S)(int) = nullptr]];
|
|
|
|
)cpp",
|
|
|
|
"VarDecl",
|
|
|
|
},
|
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
[[void ^(*S)(int)]] = nullptr;
|
|
|
|
)cpp",
|
2019-07-24 17:39:11 +08:00
|
|
|
"FunctionProtoTypeLoc",
|
2019-06-27 19:17:13 +08:00
|
|
|
},
|
2019-09-04 20:15:20 +08:00
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
struct S {
|
2019-11-14 03:16:23 +08:00
|
|
|
int foo() const;
|
|
|
|
int bar() { return [[f^oo]](); }
|
2019-09-04 20:15:20 +08:00
|
|
|
};
|
|
|
|
)cpp",
|
2019-11-14 03:16:23 +08:00
|
|
|
"MemberExpr", // Not implicit CXXThisExpr, or its implicit cast!
|
|
|
|
},
|
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
auto lambda = [](const char*){ return 0; };
|
|
|
|
int x = lambda([["y^"]]);
|
|
|
|
)cpp",
|
|
|
|
"StringLiteral", // Not DeclRefExpr to operator()!
|
2019-09-04 20:15:20 +08:00
|
|
|
},
|
2021-01-27 02:58:53 +08:00
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
struct Foo {};
|
|
|
|
struct Bar : [[v^ir^tual private Foo]] {};
|
|
|
|
)cpp",
|
|
|
|
"CXXBaseSpecifier",
|
|
|
|
},
|
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
struct Foo {};
|
|
|
|
struct Bar : private [[Fo^o]] {};
|
|
|
|
)cpp",
|
|
|
|
"RecordTypeLoc",
|
|
|
|
},
|
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
struct Foo {};
|
|
|
|
struct Bar : [[Fo^o]] {};
|
|
|
|
)cpp",
|
|
|
|
"RecordTypeLoc",
|
|
|
|
},
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
|
|
|
|
// Point selections.
|
|
|
|
{"void foo() { [[^foo]](); }", "DeclRefExpr"},
|
|
|
|
{"void foo() { [[f^oo]](); }", "DeclRefExpr"},
|
|
|
|
{"void foo() { [[fo^o]](); }", "DeclRefExpr"},
|
|
|
|
{"void foo() { [[foo^()]]; }", "CallExpr"},
|
|
|
|
{"void foo() { [[foo^]] (); }", "DeclRefExpr"},
|
|
|
|
{"int bar; void foo() [[{ foo (); }]]^", "CompoundStmt"},
|
2019-11-28 18:24:04 +08:00
|
|
|
{"int x = [[42]]^;", "IntegerLiteral"},
|
2019-06-27 19:17:13 +08:00
|
|
|
|
[clangd] Ignore semicolons, whitespace, and comments in SelectionTree.
Summary:
Whitespace and comments are a clear bugfix: selecting some
comments/space near a statement doesn't mean you're selecting the
surrounding block.
Semicolons are less obvious, but for similar reasons: these tokens
aren't actually claimed by any AST node (usually), so an AST-based model
like SelectionTree shouldn't take them into account.
Callers may still sometimes care about semis of course:
- when the selection is an expr with a non-expr parent, selection of
the semicolon indicates intent to select the statement.
- when a statement with a trailing semi is selected, we need to know
its range to ensure it can be removed.
SelectionTree may or may not play a role here, but these are separate questions
from its core function of describing which AST nodes were selected.
The mechanism here is the TokenBuffer from syntax-trees. We use it in a
fairly low-level way (just to get boundaries of raw spelled tokens). The
actual mapping of AST nodes to coordinates continues to use the (fairly
mature) SourceLocation based logic. TokenBuffer/Syntax trees
don't currently offer an alternative to getFileRange(), I think.
Reviewers: SureYeaah, kadircet
Subscribers: MaskRay, jkorous, arphaman, cfe-commits, ilya-biryukov
Tags: #clang
Differential Revision: https://reviews.llvm.org/D65486
llvm-svn: 367453
2019-08-01 01:52:40 +08:00
|
|
|
// Ignores whitespace, comments, and semicolons in the selection.
|
|
|
|
{"void foo() { [[foo^()]]; /*comment*/^}", "CallExpr"},
|
|
|
|
|
2019-06-27 19:17:13 +08:00
|
|
|
// Tricky case: FunctionTypeLoc in FunctionDecl has a hole in it.
|
2019-07-24 17:39:11 +08:00
|
|
|
{"[[^void]] foo();", "BuiltinTypeLoc"},
|
|
|
|
{"[[void foo^()]];", "FunctionProtoTypeLoc"},
|
2019-06-27 19:17:13 +08:00
|
|
|
{"[[^void foo^()]];", "FunctionDecl"},
|
|
|
|
{"[[void ^foo()]];", "FunctionDecl"},
|
|
|
|
// Tricky case: two VarDecls share a specifier.
|
|
|
|
{"[[int ^a]], b;", "VarDecl"},
|
|
|
|
{"[[int a, ^b]];", "VarDecl"},
|
2019-11-15 23:07:34 +08:00
|
|
|
// Tricky case: CXXConstructExpr wants to claim the whole init range.
|
|
|
|
{
|
|
|
|
R"cpp(
|
[clangd] Errors in TestTU cause test failures unless suppressed with error-ok.
Summary:
The historic behavior of TestTU is to gather diagnostics and otherwise ignore
them. So if a test has a syntax error, and doesn't assert diagnostics, it
silently misbehaves.
This can be annoying when developing tests, as evidenced by various tests
gaining "assert no diagnostics" where that's not really the point of the test.
This patch aims to make that default behavior. For the first error
(not warning), TestTU will call ADD_FAILURE().
This can be suppressed with a comment containing "error-ok". For now that will
suppress any errors in the TU. We can make this stricter later -verify style.
(-verify itself is hard to reuse because of DiagnosticConsumer interfaces...)
A magic-comment was chosen over a TestTU option because of table-driven tests.
In addition to the behavior change, this patch:
- adds //error-ok where we're knowingly testing invalid code
(e.g. for diagnostics, crash-resilience, or token-level tests)
- fixes a bunch of errors in the checked-in tests, mostly trivial (missing ;)
- removes a bunch of now-redundant instances of "assert no diagnostics"
Reviewers: kadircet
Subscribers: ilya-biryukov, MaskRay, jkorous, arphaman, usaxena95, cfe-commits
Tags: #clang
Differential Revision: https://reviews.llvm.org/D73199
2020-01-22 23:38:41 +08:00
|
|
|
struct X { X(int); };
|
2019-11-15 23:07:34 +08:00
|
|
|
class Y {
|
|
|
|
X x;
|
|
|
|
Y() : [[^x(4)]] {}
|
|
|
|
};
|
|
|
|
)cpp",
|
|
|
|
"CXXCtorInitializer", // Not the CXXConstructExpr!
|
|
|
|
},
|
2019-06-27 19:17:13 +08:00
|
|
|
// Tricky case: anonymous struct is a sibling of the VarDecl.
|
|
|
|
{"[[st^ruct {int x;}]] y;", "CXXRecordDecl"},
|
|
|
|
{"[[struct {int x;} ^y]];", "VarDecl"},
|
|
|
|
{"struct {[[int ^x]];} y;", "FieldDecl"},
|
2019-07-24 17:39:11 +08:00
|
|
|
// FIXME: the AST has no location info for qualifiers.
|
|
|
|
{"const [[a^uto]] x = 42;", "AutoTypeLoc"},
|
|
|
|
{"[[co^nst auto x = 42]];", "VarDecl"},
|
2019-06-27 19:17:13 +08:00
|
|
|
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
{"^", nullptr},
|
|
|
|
{"void foo() { [[foo^^]] (); }", "DeclRefExpr"},
|
|
|
|
|
|
|
|
// FIXME: Ideally we'd get a declstmt or the VarDecl itself here.
|
|
|
|
// This doesn't happen now; the RAV doesn't traverse a node containing ;.
|
|
|
|
{"int x = 42;^", nullptr},
|
|
|
|
|
[clangd] SelectionTree treats TranslationUnitDecl (mostly) consistently with other containers.
Summary:
Previously TranslationUnitDecl would never be selected.
This means root() is never null, and returns a reference.
commonAncestor() is in principle never null also, but returning TUDecl
here requires tweaks to be careful not to traverse it (this was already
possible when selecting multiple top-level decls, and there are associated bugs!)
Instead, never allow commonAncestor() to return TUDecl, return null instead.
Reviewers: hokein
Subscribers: ilya-biryukov, MaskRay, jkorous, arphaman, kadircet, cfe-commits
Tags: #clang
Differential Revision: https://reviews.llvm.org/D65101
llvm-svn: 366893
2019-07-24 20:14:56 +08:00
|
|
|
// Common ancestor is logically TUDecl, but we never return that.
|
|
|
|
{"^int x; int y;^", nullptr},
|
|
|
|
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
// Node types that have caused problems in the past.
|
2019-07-24 17:39:11 +08:00
|
|
|
{"template <typename T> void foo() { [[^T]] t; }",
|
|
|
|
"TemplateTypeParmTypeLoc"},
|
[clangd] Fix an assertion failure in Selection.
Summary:
The assertion is triggered when the Decl is null.
Details for the assertion:
F0207 09:55:09.069385 47308 logging.cc:84] assert.h assertion failed at llvm/include/llvm/Support/Casting.h:105 in static bool llvm::isa_impl_cl<clang::TranslationUnitDecl, const clang:: Decl *>::doit(const From *) [To = clang::TranslationUnitDecl, From = const clang::Decl *]: Val && "isa<> used on a null pointer"
15 *** Check failure stack trace: ***
19 @ 0x55615c1f7e06 __assert_fail
20 @ 0x55615a6297d8 clang::clangd::(anonymous namespace)::SelectionVisitor::TraverseDecl()
21 @ 0x55615a62f48d clang::RecursiveASTVisitor<>::TraverseTemplateTemplateParmDecl()
22 @ 0x55615a62b264 clang::RecursiveASTVisitor<>::TraverseDecl()
23 @ 0x55615a62979c clang::clangd::(anonymous namespace)::SelectionVisitor::TraverseDecl()
24 @ 0x55615a63060c clang::RecursiveASTVisitor<>::TraverseClassTemplatePartialSpecializationDecl()
25 @ 0x55615a62ae45 clang::RecursiveASTVisitor<>::TraverseDecl()
Reviewers: sammccall
Subscribers: javed.absar, kristof.beyls, ilya-biryukov, ioeric, MaskRay, jkorous, arphaman, kadircet, cfe-commits
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57879
llvm-svn: 353421
2019-02-08 00:00:44 +08:00
|
|
|
|
|
|
|
// No crash
|
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
template <class T> struct Foo {};
|
|
|
|
template <[[template<class> class /*cursor here*/^U]]>
|
|
|
|
struct Foo<U<int>*> {};
|
|
|
|
)cpp",
|
2019-06-25 17:36:09 +08:00
|
|
|
"TemplateTemplateParmDecl"},
|
2019-08-28 20:05:12 +08:00
|
|
|
|
|
|
|
// Foreach has a weird AST, ensure we can select parts of the range init.
|
|
|
|
// This used to fail, because the DeclStmt for C claimed the whole range.
|
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
struct Str {
|
|
|
|
const char *begin();
|
|
|
|
const char *end();
|
|
|
|
};
|
|
|
|
Str makeStr(const char*);
|
|
|
|
void loop() {
|
[clangd] Errors in TestTU cause test failures unless suppressed with error-ok.
Summary:
The historic behavior of TestTU is to gather diagnostics and otherwise ignore
them. So if a test has a syntax error, and doesn't assert diagnostics, it
silently misbehaves.
This can be annoying when developing tests, as evidenced by various tests
gaining "assert no diagnostics" where that's not really the point of the test.
This patch aims to make that default behavior. For the first error
(not warning), TestTU will call ADD_FAILURE().
This can be suppressed with a comment containing "error-ok". For now that will
suppress any errors in the TU. We can make this stricter later -verify style.
(-verify itself is hard to reuse because of DiagnosticConsumer interfaces...)
A magic-comment was chosen over a TestTU option because of table-driven tests.
In addition to the behavior change, this patch:
- adds //error-ok where we're knowingly testing invalid code
(e.g. for diagnostics, crash-resilience, or token-level tests)
- fixes a bunch of errors in the checked-in tests, mostly trivial (missing ;)
- removes a bunch of now-redundant instances of "assert no diagnostics"
Reviewers: kadircet
Subscribers: ilya-biryukov, MaskRay, jkorous, arphaman, usaxena95, cfe-commits
Tags: #clang
Differential Revision: https://reviews.llvm.org/D73199
2020-01-22 23:38:41 +08:00
|
|
|
for (const char C : [[mak^eStr("foo"^)]])
|
2019-08-28 20:05:12 +08:00
|
|
|
;
|
|
|
|
}
|
|
|
|
)cpp",
|
|
|
|
"CallExpr"},
|
2019-11-19 23:57:31 +08:00
|
|
|
|
|
|
|
// User-defined literals are tricky: is 12_i one token or two?
|
|
|
|
// For now we treat it as one, and the UserDefinedLiteral as a leaf.
|
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
struct Foo{};
|
|
|
|
Foo operator""_ud(unsigned long long);
|
|
|
|
Foo x = [[^12_ud]];
|
|
|
|
)cpp",
|
|
|
|
"UserDefinedLiteral"},
|
2020-01-14 02:53:52 +08:00
|
|
|
|
2020-01-13 19:09:30 +08:00
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
int a;
|
|
|
|
decltype([[^a]] + a) b;
|
|
|
|
)cpp",
|
|
|
|
"DeclRefExpr"},
|
2020-01-14 02:53:52 +08:00
|
|
|
|
2020-10-17 02:14:37 +08:00
|
|
|
// Objective-C nullability attributes.
|
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
@interface I{}
|
|
|
|
@property(nullable) [[^I]] *x;
|
|
|
|
@end
|
|
|
|
)cpp",
|
|
|
|
"ObjCInterfaceTypeLoc"},
|
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
@interface I{}
|
|
|
|
- (void)doSomething:(nonnull [[i^d]])argument;
|
|
|
|
@end
|
|
|
|
)cpp",
|
|
|
|
"TypedefTypeLoc"},
|
|
|
|
|
2020-01-14 02:53:52 +08:00
|
|
|
// Objective-C OpaqueValueExpr/PseudoObjectExpr has weird ASTs.
|
|
|
|
// Need to traverse the contents of the OpaqueValueExpr to the POE,
|
|
|
|
// and ensure we traverse only the syntactic form of the PseudoObjectExpr.
|
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
@interface I{}
|
|
|
|
@property(retain) I*x;
|
|
|
|
@property(retain) I*y;
|
|
|
|
@end
|
|
|
|
void test(I *f) { [[^f]].x.y = 0; }
|
|
|
|
)cpp",
|
|
|
|
"DeclRefExpr"},
|
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
@interface I{}
|
|
|
|
@property(retain) I*x;
|
|
|
|
@property(retain) I*y;
|
|
|
|
@end
|
|
|
|
void test(I *f) { [[f.^x]].y = 0; }
|
|
|
|
)cpp",
|
|
|
|
"ObjCPropertyRefExpr"},
|
|
|
|
// Examples with implicit properties.
|
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
@interface I{}
|
|
|
|
-(int)foo;
|
|
|
|
@end
|
|
|
|
int test(I *f) { return 42 + [[^f]].foo; }
|
|
|
|
)cpp",
|
|
|
|
"DeclRefExpr"},
|
|
|
|
{
|
|
|
|
R"cpp(
|
|
|
|
@interface I{}
|
|
|
|
-(int)foo;
|
|
|
|
@end
|
|
|
|
int test(I *f) { return 42 + [[f.^foo]]; }
|
|
|
|
)cpp",
|
|
|
|
"ObjCPropertyRefExpr"},
|
2020-02-25 16:33:52 +08:00
|
|
|
{"struct foo { [[int has^h<:32:>]]; };", "FieldDecl"},
|
|
|
|
{"struct foo { [[op^erator int()]]; };", "CXXConversionDecl"},
|
|
|
|
{"struct foo { [[^~foo()]]; };", "CXXDestructorDecl"},
|
|
|
|
// FIXME: The following to should be class itself instead.
|
|
|
|
{"struct foo { [[fo^o(){}]] };", "CXXConstructorDecl"},
|
2020-03-16 23:37:19 +08:00
|
|
|
|
|
|
|
{R"cpp(
|
|
|
|
struct S1 { void f(); };
|
|
|
|
struct S2 { S1 * operator->(); };
|
|
|
|
void test(S2 s2) {
|
|
|
|
s2[[-^>]]f();
|
|
|
|
}
|
2020-07-17 18:03:24 +08:00
|
|
|
)cpp",
|
2020-08-10 08:37:43 +08:00
|
|
|
"DeclRefExpr"}, // DeclRefExpr to the "operator->" method.
|
|
|
|
|
|
|
|
// Template template argument.
|
|
|
|
{R"cpp(
|
|
|
|
template <typename> class Vector {};
|
|
|
|
template <template <typename> class Container> class A {};
|
|
|
|
A<[[V^ector]]> a;
|
|
|
|
)cpp",
|
|
|
|
"TemplateArgumentLoc"}};
|
|
|
|
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
for (const Case &C : Cases) {
|
2020-05-11 17:02:34 +08:00
|
|
|
trace::TestTracer Tracer;
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
Annotations Test(C.Code);
|
2019-10-13 21:15:27 +08:00
|
|
|
|
|
|
|
TestTU TU;
|
2020-01-29 03:23:46 +08:00
|
|
|
TU.Code = std::string(Test.code());
|
2019-10-13 21:15:27 +08:00
|
|
|
|
2020-01-14 02:53:52 +08:00
|
|
|
TU.ExtraArgs.push_back("-xobjective-c++");
|
2019-10-13 21:15:27 +08:00
|
|
|
|
|
|
|
auto AST = TU.build();
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
auto T = makeSelectionTree(C.Code, AST);
|
[clangd] SelectionTree treats TranslationUnitDecl (mostly) consistently with other containers.
Summary:
Previously TranslationUnitDecl would never be selected.
This means root() is never null, and returns a reference.
commonAncestor() is in principle never null also, but returning TUDecl
here requires tweaks to be careful not to traverse it (this was already
possible when selecting multiple top-level decls, and there are associated bugs!)
Instead, never allow commonAncestor() to return TUDecl, return null instead.
Reviewers: hokein
Subscribers: ilya-biryukov, MaskRay, jkorous, arphaman, kadircet, cfe-commits
Tags: #clang
Differential Revision: https://reviews.llvm.org/D65101
llvm-svn: 366893
2019-07-24 20:14:56 +08:00
|
|
|
EXPECT_EQ("TranslationUnitDecl", nodeKind(&T.root())) << C.Code;
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
|
|
|
|
if (Test.ranges().empty()) {
|
|
|
|
// If no [[range]] is marked in the example, there should be no selection.
|
|
|
|
EXPECT_FALSE(T.commonAncestor()) << C.Code << "\n" << T;
|
2020-12-07 17:52:04 +08:00
|
|
|
EXPECT_THAT(Tracer.takeMetric("selection_recovery", "C++"),
|
|
|
|
testing::IsEmpty());
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
} else {
|
[clangd] SelectionTree treats TranslationUnitDecl (mostly) consistently with other containers.
Summary:
Previously TranslationUnitDecl would never be selected.
This means root() is never null, and returns a reference.
commonAncestor() is in principle never null also, but returning TUDecl
here requires tweaks to be careful not to traverse it (this was already
possible when selecting multiple top-level decls, and there are associated bugs!)
Instead, never allow commonAncestor() to return TUDecl, return null instead.
Reviewers: hokein
Subscribers: ilya-biryukov, MaskRay, jkorous, arphaman, kadircet, cfe-commits
Tags: #clang
Differential Revision: https://reviews.llvm.org/D65101
llvm-svn: 366893
2019-07-24 20:14:56 +08:00
|
|
|
// If there is an expected selection, common ancestor should exist
|
|
|
|
// with the appropriate node type.
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
EXPECT_EQ(C.CommonAncestorKind, nodeKind(T.commonAncestor()))
|
|
|
|
<< C.Code << "\n"
|
|
|
|
<< T;
|
|
|
|
// Convert the reported common ancestor to a range and verify it.
|
|
|
|
EXPECT_EQ(nodeRange(T.commonAncestor(), AST), Test.range())
|
|
|
|
<< C.Code << "\n"
|
|
|
|
<< T;
|
|
|
|
|
|
|
|
// Check that common ancestor is reachable on exactly one path from root,
|
|
|
|
// and no nodes outside it are selected.
|
|
|
|
EXPECT_TRUE(verifyCommonAncestor(T.root(), T.commonAncestor(), C.Code))
|
|
|
|
<< C.Code;
|
2020-12-07 17:52:04 +08:00
|
|
|
EXPECT_THAT(Tracer.takeMetric("selection_recovery", "C++"),
|
|
|
|
ElementsAreArray({0}));
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-06-18 21:37:54 +08:00
|
|
|
// Regression test: this used to match the injected X, not the outer X.
|
|
|
|
TEST(SelectionTest, InjectedClassName) {
|
2019-12-24 02:38:04 +08:00
|
|
|
const char *Code = "struct ^X { int x; };";
|
2019-06-18 21:37:54 +08:00
|
|
|
auto AST = TestTU::withCode(Annotations(Code).code()).build();
|
|
|
|
auto T = makeSelectionTree(Code, AST);
|
|
|
|
ASSERT_EQ("CXXRecordDecl", nodeKind(T.commonAncestor())) << T;
|
|
|
|
auto *D = dyn_cast<CXXRecordDecl>(T.commonAncestor()->ASTNode.get<Decl>());
|
|
|
|
EXPECT_FALSE(D->isInjectedClassName());
|
|
|
|
}
|
|
|
|
|
2020-05-11 17:02:34 +08:00
|
|
|
TEST(SelectionTree, Metrics) {
|
|
|
|
const char *Code = R"cpp(
|
|
|
|
// error-ok: testing behavior on recovery expression
|
|
|
|
int foo();
|
|
|
|
int foo(int, int);
|
|
|
|
int x = fo^o(42);
|
|
|
|
)cpp";
|
|
|
|
auto AST = TestTU::withCode(Annotations(Code).code()).build();
|
|
|
|
trace::TestTracer Tracer;
|
|
|
|
auto T = makeSelectionTree(Code, AST);
|
2020-12-07 17:52:04 +08:00
|
|
|
EXPECT_THAT(Tracer.takeMetric("selection_recovery", "C++"),
|
|
|
|
ElementsAreArray({1}));
|
|
|
|
EXPECT_THAT(Tracer.takeMetric("selection_recovery_type", "C++"),
|
|
|
|
ElementsAreArray({1}));
|
2020-05-11 17:02:34 +08:00
|
|
|
}
|
|
|
|
|
2019-07-19 19:41:02 +08:00
|
|
|
// FIXME: Doesn't select the binary operator node in
|
|
|
|
// #define FOO(X) X + 1
|
|
|
|
// int a, b = [[FOO(a)]];
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
TEST(SelectionTest, Selected) {
|
|
|
|
// Selection with ^marks^.
|
|
|
|
// Partially selected nodes marked with a [[range]].
|
|
|
|
// Completely selected nodes marked with a $C[[range]].
|
|
|
|
const char *Cases[] = {
|
|
|
|
R"cpp( int abc, xyz = [[^ab^c]]; )cpp",
|
|
|
|
R"cpp( int abc, xyz = [[a^bc^]]; )cpp",
|
|
|
|
R"cpp( int abc, xyz = $C[[^abc^]]; )cpp",
|
|
|
|
R"cpp(
|
|
|
|
void foo() {
|
|
|
|
[[if ([[1^11]]) $C[[{
|
|
|
|
$C[[return]];
|
|
|
|
}]] else [[{^
|
|
|
|
}]]]]
|
2019-12-03 23:59:52 +08:00
|
|
|
char z;
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
}
|
|
|
|
)cpp",
|
2019-02-21 03:26:39 +08:00
|
|
|
R"cpp(
|
|
|
|
template <class T>
|
|
|
|
struct unique_ptr {};
|
2019-07-19 19:41:02 +08:00
|
|
|
void foo(^$C[[unique_ptr<$C[[unique_ptr<$C[[int]]>]]>]]^ a) {}
|
|
|
|
)cpp",
|
|
|
|
R"cpp(int a = [[5 >^> 1]];)cpp",
|
2019-12-03 23:59:52 +08:00
|
|
|
R"cpp(
|
2019-07-19 19:41:02 +08:00
|
|
|
#define ECHO(X) X
|
2019-12-03 23:59:52 +08:00
|
|
|
ECHO(EC^HO($C[[int]]) EC^HO(a));
|
|
|
|
)cpp",
|
2019-10-02 18:01:53 +08:00
|
|
|
R"cpp( $C[[^$C[[int]] a^]]; )cpp",
|
|
|
|
R"cpp( $C[[^$C[[int]] a = $C[[5]]^]]; )cpp",
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
};
|
|
|
|
for (const char *C : Cases) {
|
|
|
|
Annotations Test(C);
|
|
|
|
auto AST = TestTU::withCode(Test.code()).build();
|
|
|
|
auto T = makeSelectionTree(C, AST);
|
|
|
|
|
|
|
|
std::vector<Range> Complete, Partial;
|
|
|
|
for (const SelectionTree::Node *N : allNodes(T))
|
|
|
|
if (N->Selected == SelectionTree::Complete)
|
|
|
|
Complete.push_back(nodeRange(N, AST));
|
|
|
|
else if (N->Selected == SelectionTree::Partial)
|
|
|
|
Partial.push_back(nodeRange(N, AST));
|
|
|
|
EXPECT_THAT(Complete, UnorderedElementsAreArray(Test.ranges("C"))) << C;
|
|
|
|
EXPECT_THAT(Partial, UnorderedElementsAreArray(Test.ranges())) << C;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-08-27 16:44:06 +08:00
|
|
|
TEST(SelectionTest, PathologicalPreprocessor) {
|
|
|
|
const char *Case = R"cpp(
|
|
|
|
#define MACRO while(1)
|
|
|
|
void test() {
|
|
|
|
#include "Expand.inc"
|
|
|
|
br^eak;
|
|
|
|
}
|
|
|
|
)cpp";
|
|
|
|
Annotations Test(Case);
|
|
|
|
auto TU = TestTU::withCode(Test.code());
|
|
|
|
TU.AdditionalFiles["Expand.inc"] = "MACRO\n";
|
|
|
|
auto AST = TU.build();
|
2021-03-15 17:18:12 +08:00
|
|
|
EXPECT_THAT(*AST.getDiagnostics(), ::testing::IsEmpty());
|
2019-08-27 16:44:06 +08:00
|
|
|
auto T = makeSelectionTree(Case, AST);
|
|
|
|
|
|
|
|
EXPECT_EQ("BreakStmt", T.commonAncestor()->kind());
|
|
|
|
EXPECT_EQ("WhileStmt", T.commonAncestor()->Parent->kind());
|
|
|
|
}
|
|
|
|
|
2019-12-03 23:59:52 +08:00
|
|
|
TEST(SelectionTest, IncludedFile) {
|
|
|
|
const char *Case = R"cpp(
|
|
|
|
void test() {
|
|
|
|
#include "Exp^and.inc"
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
)cpp";
|
|
|
|
Annotations Test(Case);
|
|
|
|
auto TU = TestTU::withCode(Test.code());
|
|
|
|
TU.AdditionalFiles["Expand.inc"] = "while(1)\n";
|
|
|
|
auto AST = TU.build();
|
|
|
|
auto T = makeSelectionTree(Case, AST);
|
|
|
|
|
2020-07-17 18:03:24 +08:00
|
|
|
EXPECT_EQ(nullptr, T.commonAncestor());
|
2019-12-03 23:59:52 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
TEST(SelectionTest, MacroArgExpansion) {
|
2019-12-24 02:38:04 +08:00
|
|
|
// If a macro arg is expanded several times, we only consider the first one
|
|
|
|
// selected.
|
2019-12-03 23:59:52 +08:00
|
|
|
const char *Case = R"cpp(
|
|
|
|
int mul(int, int);
|
|
|
|
#define SQUARE(X) mul(X, X);
|
|
|
|
int nine = SQUARE(^3);
|
|
|
|
)cpp";
|
|
|
|
Annotations Test(Case);
|
|
|
|
auto AST = TestTU::withCode(Test.code()).build();
|
|
|
|
auto T = makeSelectionTree(Case, AST);
|
2019-12-24 02:38:04 +08:00
|
|
|
EXPECT_EQ("IntegerLiteral", T.commonAncestor()->kind());
|
|
|
|
EXPECT_TRUE(T.commonAncestor()->Selected);
|
2019-12-03 23:59:52 +08:00
|
|
|
|
|
|
|
// Verify that the common assert() macro doesn't suffer from this.
|
|
|
|
// (This is because we don't associate the stringified token with the arg).
|
|
|
|
Case = R"cpp(
|
|
|
|
void die(const char*);
|
[clangd] Errors in TestTU cause test failures unless suppressed with error-ok.
Summary:
The historic behavior of TestTU is to gather diagnostics and otherwise ignore
them. So if a test has a syntax error, and doesn't assert diagnostics, it
silently misbehaves.
This can be annoying when developing tests, as evidenced by various tests
gaining "assert no diagnostics" where that's not really the point of the test.
This patch aims to make that default behavior. For the first error
(not warning), TestTU will call ADD_FAILURE().
This can be suppressed with a comment containing "error-ok". For now that will
suppress any errors in the TU. We can make this stricter later -verify style.
(-verify itself is hard to reuse because of DiagnosticConsumer interfaces...)
A magic-comment was chosen over a TestTU option because of table-driven tests.
In addition to the behavior change, this patch:
- adds //error-ok where we're knowingly testing invalid code
(e.g. for diagnostics, crash-resilience, or token-level tests)
- fixes a bunch of errors in the checked-in tests, mostly trivial (missing ;)
- removes a bunch of now-redundant instances of "assert no diagnostics"
Reviewers: kadircet
Subscribers: ilya-biryukov, MaskRay, jkorous, arphaman, usaxena95, cfe-commits
Tags: #clang
Differential Revision: https://reviews.llvm.org/D73199
2020-01-22 23:38:41 +08:00
|
|
|
#define assert(x) (x ? (void)0 : die(#x))
|
2019-12-03 23:59:52 +08:00
|
|
|
void foo() { assert(^42); }
|
|
|
|
)cpp";
|
|
|
|
Test = Annotations(Case);
|
|
|
|
AST = TestTU::withCode(Test.code()).build();
|
|
|
|
T = makeSelectionTree(Case, AST);
|
|
|
|
|
|
|
|
EXPECT_EQ("IntegerLiteral", T.commonAncestor()->kind());
|
|
|
|
}
|
|
|
|
|
2019-07-26 23:29:52 +08:00
|
|
|
TEST(SelectionTest, Implicit) {
|
2019-12-24 02:38:04 +08:00
|
|
|
const char *Test = R"cpp(
|
2019-07-26 23:29:52 +08:00
|
|
|
struct S { S(const char*); };
|
|
|
|
int f(S);
|
|
|
|
int x = f("^");
|
|
|
|
)cpp";
|
|
|
|
auto AST = TestTU::withCode(Annotations(Test).code()).build();
|
|
|
|
auto T = makeSelectionTree(Test, AST);
|
|
|
|
|
|
|
|
const SelectionTree::Node *Str = T.commonAncestor();
|
|
|
|
EXPECT_EQ("StringLiteral", nodeKind(Str)) << "Implicit selected?";
|
|
|
|
EXPECT_EQ("ImplicitCastExpr", nodeKind(Str->Parent));
|
|
|
|
EXPECT_EQ("CXXConstructExpr", nodeKind(Str->Parent->Parent));
|
|
|
|
EXPECT_EQ(Str, &Str->Parent->Parent->ignoreImplicit())
|
|
|
|
<< "Didn't unwrap " << nodeKind(&Str->Parent->Parent->ignoreImplicit());
|
2019-08-10 07:40:54 +08:00
|
|
|
|
|
|
|
EXPECT_EQ("CXXConstructExpr", nodeKind(&Str->outerImplicit()));
|
2019-07-26 23:29:52 +08:00
|
|
|
}
|
|
|
|
|
2020-02-24 03:03:00 +08:00
|
|
|
TEST(SelectionTest, CreateAll) {
|
|
|
|
llvm::Annotations Test("int$unique^ a=1$ambiguous^+1; $empty^");
|
|
|
|
auto AST = TestTU::withCode(Test.code()).build();
|
|
|
|
unsigned Seen = 0;
|
|
|
|
SelectionTree::createEach(
|
|
|
|
AST.getASTContext(), AST.getTokens(), Test.point("ambiguous"),
|
|
|
|
Test.point("ambiguous"), [&](SelectionTree T) {
|
|
|
|
// Expect to see the right-biased tree first.
|
2021-06-10 01:19:49 +08:00
|
|
|
if (Seen == 0) {
|
2020-02-24 03:03:00 +08:00
|
|
|
EXPECT_EQ("BinaryOperator", nodeKind(T.commonAncestor()));
|
2021-06-10 01:19:49 +08:00
|
|
|
} else if (Seen == 1) {
|
2020-02-24 03:03:00 +08:00
|
|
|
EXPECT_EQ("IntegerLiteral", nodeKind(T.commonAncestor()));
|
2021-06-10 01:19:49 +08:00
|
|
|
}
|
2020-02-24 03:03:00 +08:00
|
|
|
++Seen;
|
|
|
|
return false;
|
|
|
|
});
|
|
|
|
EXPECT_EQ(2u, Seen);
|
|
|
|
|
|
|
|
Seen = 0;
|
|
|
|
SelectionTree::createEach(AST.getASTContext(), AST.getTokens(),
|
|
|
|
Test.point("ambiguous"), Test.point("ambiguous"),
|
|
|
|
[&](SelectionTree T) {
|
|
|
|
++Seen;
|
|
|
|
return true;
|
|
|
|
});
|
|
|
|
EXPECT_EQ(1u, Seen) << "Return true --> stop iterating";
|
|
|
|
|
|
|
|
Seen = 0;
|
|
|
|
SelectionTree::createEach(AST.getASTContext(), AST.getTokens(),
|
|
|
|
Test.point("unique"), Test.point("unique"),
|
|
|
|
[&](SelectionTree T) {
|
|
|
|
++Seen;
|
|
|
|
return false;
|
|
|
|
});
|
|
|
|
EXPECT_EQ(1u, Seen) << "no ambiguity --> only one tree";
|
|
|
|
|
|
|
|
Seen = 0;
|
|
|
|
SelectionTree::createEach(AST.getASTContext(), AST.getTokens(),
|
|
|
|
Test.point("empty"), Test.point("empty"),
|
|
|
|
[&](SelectionTree T) {
|
|
|
|
EXPECT_FALSE(T.commonAncestor());
|
|
|
|
++Seen;
|
|
|
|
return false;
|
|
|
|
});
|
|
|
|
EXPECT_EQ(1u, Seen) << "empty tree still created";
|
|
|
|
|
|
|
|
Seen = 0;
|
|
|
|
SelectionTree::createEach(AST.getASTContext(), AST.getTokens(),
|
|
|
|
Test.point("unique"), Test.point("ambiguous"),
|
|
|
|
[&](SelectionTree T) {
|
|
|
|
++Seen;
|
|
|
|
return false;
|
|
|
|
});
|
|
|
|
EXPECT_EQ(1u, Seen) << "one tree for nontrivial selection";
|
|
|
|
}
|
|
|
|
|
[clangd] Lib to compute and represent selection under cursor.
Summary:
The primary problem this solves is to expose the codeAction selection to
AST-based refactorings in a way that makes it easy and efficient for them to
bind to the right parts of the AST.
It should also allow us to make XRefs based features (textDocument/definition)
more robust, more easily implement textDocument/typeDefinition etc.
As an example, template parameter references can be identified without special
handling.
There should be slight speedup too: we can prune most of the AST traversal
in most cases.
Elephant in the room: this is similar-but-different to Tooling/Refactoring/ASTSelection.
That captures a smaller set of AST nodes, has a slightly different way of
representing selections, and generally has mare features and does more work.
The overall shape is pretty similar, and yet I can't quite get to behave as I
expect.
Reviewers: ilya-biryukov, kadircet
Subscribers: mgorny, ioeric, MaskRay, jkorous, mgrang, arphaman
Tags: #clang
Differential Revision: https://reviews.llvm.org/D57562
llvm-svn: 352874
2019-02-01 23:05:11 +08:00
|
|
|
} // namespace
|
|
|
|
} // namespace clangd
|
|
|
|
} // namespace clang
|