mirror of
https://github.com/LadybirdBrowser/ladybird.git
synced 2024-11-26 17:40:27 +00:00
HackStudio+LanguageServers/Cpp: Show scope of symbols in Locator
This commit is contained in:
parent
6054a418e5
commit
84e34d76d8
Notes:
sideshowbarker
2024-07-18 21:07:23 +09:00
Author: https://github.com/itamar8910 Commit: https://github.com/SerenityOS/serenity/commit/84e34d76d84 Pull-request: https://github.com/SerenityOS/serenity/pull/5924
10 changed files with 52 additions and 13 deletions
|
@ -1,6 +1,8 @@
|
||||||
#include "other.h"
|
#include "other.h"
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
|
|
||||||
|
namespace MyNamespace {
|
||||||
|
|
||||||
int func()
|
int func()
|
||||||
{
|
{
|
||||||
int x = 1;
|
int x = 1;
|
||||||
|
@ -12,3 +14,5 @@ int func()
|
||||||
printf("x+y: %d\n", x + y);
|
printf("x+y: %d\n", x + y);
|
||||||
return x + y;
|
return x + y;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
|
@ -1,3 +1,6 @@
|
||||||
|
|
||||||
|
namespace MyNamespace {
|
||||||
|
|
||||||
int func();
|
int func();
|
||||||
|
|
||||||
#define USE_VAR2
|
#define USE_VAR2
|
||||||
|
@ -12,3 +15,5 @@ struct StructInHeader {
|
||||||
int var3;
|
int var3;
|
||||||
#endif
|
#endif
|
||||||
};
|
};
|
||||||
|
|
||||||
|
}
|
||||||
|
|
|
@ -98,6 +98,7 @@ inline bool encode(Encoder& encoder, const GUI::AutocompleteProvider::Declaratio
|
||||||
if (!encode(encoder, declaration.position))
|
if (!encode(encoder, declaration.position))
|
||||||
return false;
|
return false;
|
||||||
encoder << (u32)declaration.type;
|
encoder << (u32)declaration.type;
|
||||||
|
encoder << declaration.scope;
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -109,10 +110,14 @@ inline bool decode(Decoder& decoder, GUI::AutocompleteProvider::Declaration& dec
|
||||||
|
|
||||||
if (!decode(decoder, declaration.position))
|
if (!decode(decoder, declaration.position))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
u32 type;
|
u32 type;
|
||||||
if (!decoder.decode(type))
|
if (!decoder.decode(type))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
|
if (!decoder.decode(declaration.scope))
|
||||||
|
return false;
|
||||||
|
|
||||||
declaration.type = static_cast<GUI::AutocompleteProvider::DeclarationType>(type);
|
declaration.type = static_cast<GUI::AutocompleteProvider::DeclarationType>(type);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
|
@ -294,8 +294,7 @@ NonnullRefPtrVector<Declaration> ParserAutoComplete::get_global_declarations(con
|
||||||
|
|
||||||
for (auto& decl : node.declarations()) {
|
for (auto& decl : node.declarations()) {
|
||||||
declarations.append(decl);
|
declarations.append(decl);
|
||||||
if(decl.is_namespace())
|
if (decl.is_namespace()) {
|
||||||
{
|
|
||||||
declarations.append(get_global_declarations(decl));
|
declarations.append(get_global_declarations(decl));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -410,13 +409,12 @@ void ParserAutoComplete::update_declared_symbols(const DocumentData& document)
|
||||||
{
|
{
|
||||||
Vector<GUI::AutocompleteProvider::Declaration> declarations;
|
Vector<GUI::AutocompleteProvider::Declaration> declarations;
|
||||||
|
|
||||||
for(auto& decl : get_global_declarations(*document.parser().root_node()))
|
for (auto& decl : get_global_declarations(*document.parser().root_node())) {
|
||||||
{
|
declarations.append({ decl.name(), { document.filename(), decl.start().line, decl.start().column }, type_of_declaration(decl), scope_of_declaration(decl) });
|
||||||
declarations.append({ decl.name(), { document.filename(), decl.start().line, decl.start().column }, type_of_declaration(decl) });
|
|
||||||
}
|
}
|
||||||
|
|
||||||
for (auto& definition : document.preprocessor().definitions()) {
|
for (auto& definition : document.preprocessor().definitions()) {
|
||||||
declarations.append({ definition.key, { document.filename(), definition.value.line, definition.value.column }, GUI::AutocompleteProvider::DeclarationType::PreprocessorDefinition });
|
declarations.append({ definition.key, { document.filename(), definition.value.line, definition.value.column }, GUI::AutocompleteProvider::DeclarationType::PreprocessorDefinition, {} });
|
||||||
}
|
}
|
||||||
|
|
||||||
set_declarations_of_document(document.filename(), move(declarations));
|
set_declarations_of_document(document.filename(), move(declarations));
|
||||||
|
@ -460,4 +458,27 @@ OwnPtr<ParserAutoComplete::DocumentData> ParserAutoComplete::create_document_dat
|
||||||
return document_data;
|
return document_data;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
String ParserAutoComplete::scope_of_declaration(const Declaration& decl)
|
||||||
|
{
|
||||||
|
|
||||||
|
auto parent = decl.parent();
|
||||||
|
if (!parent)
|
||||||
|
return {};
|
||||||
|
|
||||||
|
if (!parent->is_declaration())
|
||||||
|
return {};
|
||||||
|
|
||||||
|
auto& parent_decl = static_cast<Declaration&>(*parent);
|
||||||
|
|
||||||
|
if (parent_decl.is_namespace()) {
|
||||||
|
auto& containing_namespace = static_cast<NamespaceDeclaration&>(parent_decl);
|
||||||
|
auto scope_of_parent = scope_of_declaration(parent_decl);
|
||||||
|
if (scope_of_parent.is_null())
|
||||||
|
return containing_namespace.m_name;
|
||||||
|
return String::formatted("{}::{}", scope_of_parent, containing_namespace.m_name);
|
||||||
|
}
|
||||||
|
|
||||||
|
return {};
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -107,6 +107,7 @@ private:
|
||||||
String document_path_from_include_path(const StringView& include_path) const;
|
String document_path_from_include_path(const StringView& include_path) const;
|
||||||
void update_declared_symbols(const DocumentData&);
|
void update_declared_symbols(const DocumentData&);
|
||||||
GUI::AutocompleteProvider::DeclarationType type_of_declaration(const Declaration&);
|
GUI::AutocompleteProvider::DeclarationType type_of_declaration(const Declaration&);
|
||||||
|
String scope_of_declaration(const Declaration&);
|
||||||
Optional<GUI::AutocompleteProvider::ProjectLocation> find_preprocessor_definition(const DocumentData&, const GUI::TextPosition&);
|
Optional<GUI::AutocompleteProvider::ProjectLocation> find_preprocessor_definition(const DocumentData&, const GUI::TextPosition&);
|
||||||
|
|
||||||
OwnPtr<DocumentData> create_document_data(String&& text, const String& filename);
|
OwnPtr<DocumentData> create_document_data(String&& text, const String& filename);
|
||||||
|
|
|
@ -233,7 +233,7 @@ void AutoComplete::update_declared_symbols(const DocumentData& document)
|
||||||
|
|
||||||
if (!name.is_empty()) {
|
if (!name.is_empty()) {
|
||||||
dbgln("Found variable {}", name);
|
dbgln("Found variable {}", name);
|
||||||
declarations.append({ move(name), { filename, entry.name->position().start_line.line_number, entry.name->position().start_line.line_column }, GUI::AutocompleteProvider::DeclarationType::Variable });
|
declarations.append({ move(name), { filename, entry.name->position().start_line.line_number, entry.name->position().start_line.line_column }, GUI::AutocompleteProvider::DeclarationType::Variable, {} });
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
::Shell::AST::NodeVisitor::visit(node);
|
::Shell::AST::NodeVisitor::visit(node);
|
||||||
|
@ -242,7 +242,7 @@ void AutoComplete::update_declared_symbols(const DocumentData& document)
|
||||||
void visit(const ::Shell::AST::FunctionDeclaration* node) override
|
void visit(const ::Shell::AST::FunctionDeclaration* node) override
|
||||||
{
|
{
|
||||||
dbgln("Found function {}", node->name().name);
|
dbgln("Found function {}", node->name().name);
|
||||||
declarations.append({ node->name().name, { filename, node->position().start_line.line_number, node->position().start_line.line_column }, GUI::AutocompleteProvider::DeclarationType::Function });
|
declarations.append({ node->name().name, { filename, node->position().start_line.line_number, node->position().start_line.line_column }, GUI::AutocompleteProvider::DeclarationType::Function, {} });
|
||||||
}
|
}
|
||||||
|
|
||||||
const String& filename;
|
const String& filename;
|
||||||
|
|
|
@ -77,8 +77,11 @@ public:
|
||||||
return GUI::FileIconProvider::icon_for_path(suggestion.as_filename.value());
|
return GUI::FileIconProvider::icon_for_path(suggestion.as_filename.value());
|
||||||
}
|
}
|
||||||
if (suggestion.is_symbol_declaration()) {
|
if (suggestion.is_symbol_declaration()) {
|
||||||
if (index.column() == Column::Name)
|
if (index.column() == Column::Name) {
|
||||||
return suggestion.as_symbol_declaration.value().name;
|
if (suggestion.as_symbol_declaration.value().scope.is_null())
|
||||||
|
return suggestion.as_symbol_declaration.value().name;
|
||||||
|
return String::formatted("{}::{}", suggestion.as_symbol_declaration.value().scope, suggestion.as_symbol_declaration.value().name);
|
||||||
|
}
|
||||||
if (index.column() == Column::Filename)
|
if (index.column() == Column::Filename)
|
||||||
return suggestion.as_symbol_declaration.value().position.file;
|
return suggestion.as_symbol_declaration.value().position.file;
|
||||||
if (index.column() == Column::Icon) {
|
if (index.column() == Column::Icon) {
|
||||||
|
@ -225,7 +228,7 @@ void Locator::update_suggestions()
|
||||||
|
|
||||||
for (auto& item : m_document_to_declarations) {
|
for (auto& item : m_document_to_declarations) {
|
||||||
for (auto& decl : item.value) {
|
for (auto& decl : item.value) {
|
||||||
if (decl.name.contains(typed_text, CaseSensitivity::CaseInsensitive))
|
if (decl.name.contains(typed_text, CaseSensitivity::CaseInsensitive) || decl.scope.contains(typed_text, CaseSensitivity::CaseInsensitive))
|
||||||
suggestions.append((LocatorSuggestionModel::Suggestion::create_symbol_declaration(decl)));
|
suggestions.append((LocatorSuggestionModel::Suggestion::create_symbol_declaration(decl)));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -75,6 +75,7 @@ public:
|
||||||
virtual bool is_variable_or_parameter_declaration() const { return false; }
|
virtual bool is_variable_or_parameter_declaration() const { return false; }
|
||||||
virtual bool is_function_call() const { return false; }
|
virtual bool is_function_call() const { return false; }
|
||||||
virtual bool is_type() const { return false; }
|
virtual bool is_type() const { return false; }
|
||||||
|
virtual bool is_declaration() const { return false; }
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
ASTNode(ASTNode* parent, Optional<Position> start, Optional<Position> end, const String& filename)
|
ASTNode(ASTNode* parent, Optional<Position> start, Optional<Position> end, const String& filename)
|
||||||
|
@ -113,7 +114,6 @@ public:
|
||||||
virtual ~Statement() override = default;
|
virtual ~Statement() override = default;
|
||||||
virtual const char* class_name() const override { return "Statement"; }
|
virtual const char* class_name() const override { return "Statement"; }
|
||||||
|
|
||||||
virtual bool is_declaration() const { return false; }
|
|
||||||
virtual NonnullRefPtrVector<Declaration> declarations() const override;
|
virtual NonnullRefPtrVector<Declaration> declarations() const override;
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
|
|
|
@ -121,7 +121,6 @@ private:
|
||||||
NonnullRefPtrVector<Declaration> parse_declarations_in_translation_unit(ASTNode& parent);
|
NonnullRefPtrVector<Declaration> parse_declarations_in_translation_unit(ASTNode& parent);
|
||||||
RefPtr<Declaration> parse_single_declaration_in_translation_unit(ASTNode& parent);
|
RefPtr<Declaration> parse_single_declaration_in_translation_unit(ASTNode& parent);
|
||||||
|
|
||||||
|
|
||||||
bool match(Token::Type);
|
bool match(Token::Type);
|
||||||
Token consume(Token::Type);
|
Token consume(Token::Type);
|
||||||
Token consume();
|
Token consume();
|
||||||
|
|
|
@ -75,6 +75,7 @@ public:
|
||||||
String name;
|
String name;
|
||||||
ProjectLocation position;
|
ProjectLocation position;
|
||||||
DeclarationType type;
|
DeclarationType type;
|
||||||
|
String scope;
|
||||||
};
|
};
|
||||||
|
|
||||||
virtual void provide_completions(Function<void(Vector<Entry>)>) = 0;
|
virtual void provide_completions(Function<void(Vector<Entry>)>) = 0;
|
||||||
|
|
Loading…
Reference in a new issue