refactor: tests and format the world (#314)

This commit is contained in:
ykiko
2025-11-30 15:21:27 +08:00
committed by GitHub
parent 2214d53ea5
commit cec13ec29b
201 changed files with 8302 additions and 8277 deletions

View File

@@ -73,7 +73,7 @@ SpaceBeforeParensOptions:
AfterFunctionDeclarationName: false
AfterFunctionDefinitionName: false
AfterIfMacros: false
AfterOverloadedOperator: true
AfterOverloadedOperator: false
AfterRequiresInClause: true
AfterRequiresInExpression: false
BeforeNonEmptyParentheses: false
@@ -93,11 +93,50 @@ SpacesInParensOptions:
SpacesInSquareBrackets: false
WrapNamespaceBodyWithEmptyLines: Always
# Order
QualifierAlignment: Custom
QualifierOrder: ["constexpr", "const", "inline", "static", "type"]
SortIncludes: Never
SortIncludes: true
SortUsingDeclarations: Never
IncludeBlocks: Merge
IncludeBlocks: Regroup
IncludeCategories:
- Regex: '^["<](spdlog|toml\+\+|coraing|cpptrace|flatbuffers)/'
Priority: 30
SortPriority: 31
- Regex: '^["<](llvm)/'
Priority: 30
SortPriority: 32
- Regex: '^["<](clang)/'
Priority: 30
SortPriority: 33
- Regex: '^["<](clang-tidy)/'
Priority: 30
SortPriority: 34
- Regex: '^["<](Test)/'
Priority: 20
SortPriority: 22
- Regex: "^<.*"
Priority: 10
SortPriority: 10
- Regex: '^".*/.*"'
Priority: 20
SortPriority: 23
- Regex: ".*"
Priority: 20
SortPriority: 21
ForEachMacros: ["REFLECTABLE_RECORD"]
NamespaceMacros: [TEST_SUITE]
KeepEmptyLines:
AtEndOfFile: false
AtStartOfBlock: false
AtStartOfFile: false

View File

@@ -80,6 +80,7 @@ jobs:
shell: bash
run: |
if [[ "${{ runner.os }}" == "macOS" ]]; then
export SDKROOT=$(xcrun --show-sdk-path)
export PATH="/opt/homebrew/opt/llvm@20/bin:/opt/homebrew/opt/lld@20/bin:$PATH"
fi

View File

@@ -149,5 +149,5 @@ if(CLICE_ENABLE_TEST)
"${PROJECT_SOURCE_DIR}/bin/unit_tests.cc"
)
target_include_directories(unit_tests PUBLIC "${PROJECT_SOURCE_DIR}")
target_link_libraries(unit_tests PRIVATE clice-core)
target_link_libraries(unit_tests PRIVATE clice-core cpptrace::cpptrace)
endif()

View File

@@ -1,12 +1,12 @@
#include "Server/Version.h"
#include "Server/Server.h"
#include "Support/Logging.h"
#include "Server/Version.h"
#include "Support/Format.h"
#include "Support/Logging.h"
#include "llvm/Support/InitLLVM.h"
#include "llvm/Support/CommandLine.h"
#include "llvm/Support/Process.h"
#include "llvm/ADT/StringSwitch.h"
#include "llvm/Support/CommandLine.h"
#include "llvm/Support/InitLLVM.h"
#include "llvm/Support/Process.h"
namespace cl = llvm::cl;
using namespace clice;

View File

@@ -1,6 +1,6 @@
#include "Test/Test.h"
#include "Support/Logging.h"
#include "Support/GlobPattern.h"
#include "Support/Logging.h"
#include "llvm/ADT/SmallString.h"
#include "llvm/Support/CommandLine.h"
@@ -9,11 +9,6 @@
using namespace clice;
using namespace clice::testing;
constexpr static std::string_view GREEN = "\033[32m";
constexpr static std::string_view YELLOW = "\033[33m";
constexpr static std::string_view RED = "\033[31m";
constexpr static std::string_view CLEAR = "\033[0m";
namespace {
namespace cl = llvm::cl;
@@ -40,145 +35,8 @@ cl::opt<bool> enable_example{
cl::cat(unittest_category),
};
std::optional<GlobPattern> pattern;
} // namespace
namespace clice::testing {
Runner& Runner::instance() {
static Runner runner;
return runner;
}
void Runner::add_suite(std::string_view name, Suite suite) {
suites[name].emplace_back(suite);
}
void Runner::on_test(std::string_view name, Test test, bool skipped) {
std::string full_name = std::format("{}.{}", curr_suite_name, name);
/// If this test if filter, directly return.
if(pattern && !pattern->match(full_name)) {
return;
}
/// If there is any test in the suite, we print the suite start info.
if(all_skipped) {
std::println("{}[----------] tests from {}{}", GREEN, curr_suite_name, CLEAR);
all_skipped = false;
}
if(skipped) {
/// If this test is marked as skipped, only print skip information.
std::println("{}[ SKIPPED ] {}{}", YELLOW, full_name, CLEAR);
return;
}
/// Reset whether this test is failed or fatal.
curr_failed = false;
curr_fatal = false;
using namespace std::chrono;
std::println("{}[ RUN ] {}.{}{}", GREEN, curr_suite_name, name, CLEAR);
auto begin = system_clock::now();
test();
auto duration = duration_cast<milliseconds>(system_clock::now() - begin);
std::println("{}[ {} ] {} ({} ms){}",
curr_failed ? RED : GREEN,
curr_failed ? "FAILED" : " OK",
full_name,
duration.count(),
CLEAR);
/// Update test information.
curr_tests_count += 1;
total_tests_count += 1;
curr_test_duration += duration;
total_test_duration += duration;
if(curr_failed) {
curr_failed_tests_count += 1;
total_failed_tests_count += 1;
}
}
void Runner::fail(const may_failure& failure) {
if(failure.failed) {
curr_failed = true;
std::println("{}Failure at {}:{}:{}! [{}]{}",
RED,
failure.location.file_name(),
failure.location.line(),
failure.location.column(),
failure.expression,
CLEAR);
std::println("{}", failure.message);
}
if(failure.fatal) {
curr_fatal = true;
std::println("{}--> Test stopped due to fatal error.{}", RED, CLEAR);
std::exit(1);
}
}
int Runner::run_tests() {
/// Register all tests.
std::println("{}[----------] Global test environment set-up.{}", GREEN, CLEAR);
for(auto& [suite_name, suite]: suites) {
if(!enable_example && suite_name == "TEST.Example") {
continue;
}
if(!test_filter.empty()) {
auto pos = test_filter.find_first_of('.');
if(pos != std::string::npos && test_filter.substr(0, pos) != suite_name) {
continue;
}
}
curr_fatal = false;
all_skipped = true;
curr_suite_name = suite_name;
curr_tests_count = 0;
curr_failed_tests_count = 0;
curr_test_duration = std::chrono::milliseconds();
for(auto& callback: suite) {
callback();
}
/// If there is any test in the suite, we print the suite info.
if(!all_skipped) {
total_suites_count += 1;
std::println("{}[----------] {} tests from {} ({} ms total)\n{}",
GREEN,
curr_tests_count,
suite_name,
total_test_duration.count(),
CLEAR);
}
}
std::println("{}[----------] Global test environment tear-down{}", GREEN, CLEAR);
std::println("{}[==========] {} tests from {} test suites ran. ({} ms total){}",
GREEN,
total_tests_count,
total_suites_count,
total_test_duration.count(),
CLEAR);
return total_failed_tests_count != 0;
}
} // namespace clice::testing
int main(int argc, const char* argv[]) {
llvm::sys::PrintStackTraceOnErrorSignal(argv[0]);
llvm::cl::HideUnrelatedOptions(unittest_category);
@@ -186,17 +44,11 @@ int main(int argc, const char* argv[]) {
logging::stderr_logger("clice", logging::options);
if(!test_filter.empty()) {
if(auto result = GlobPattern::create(test_filter)) {
pattern.emplace(std::move(*result));
}
}
if(auto result = fs::init_resource_dir(argv[0]); !result) {
std::println("Failed to get resource directory, because {}", result.error());
return 1;
}
using namespace clice::testing;
return Runner::instance().run_tests();
return Runner2::instance().run_tests(test_filter);
}

View File

@@ -117,6 +117,7 @@ FetchContent_Declare(
GIT_TAG v4.4.2
)
set(ENABLE_ROARING_TESTS OFF CACHE INTERNAL "" FORCE)
set(ENABLE_ROARING_MICROBENCHMARKS OFF CACHE INTERNAL "" FORCE)
# flatbuffers
FetchContent_Declare(
@@ -128,7 +129,14 @@ set(FLATBUFFERS_BUILD_GRPC OFF CACHE BOOL "" FORCE)
set(FLATBUFFERS_BUILD_TESTS OFF CACHE BOOL "" FORCE)
set(FLATBUFFERS_BUILD_FLATHASH OFF CACHE BOOL "" FORCE)
FetchContent_MakeAvailable(libuv spdlog tomlplusplus croaring flatbuffers)
# cpptrace
FetchContent_Declare(
cpptrace
GIT_REPOSITORY https://github.com/jeremy-rifkin/cpptrace.git
GIT_TAG v1.0.4
)
FetchContent_MakeAvailable(libuv spdlog tomlplusplus croaring flatbuffers cpptrace)
if(WIN32)
target_compile_definitions(uv_a PRIVATE _CRT_SECURE_NO_WARNINGS)

View File

@@ -58,4 +58,5 @@ struct Widget {
template <typename T>
Widget(T) -> Widget<typename T::value_type>;
} // namespace foo

View File

@@ -1,7 +1,7 @@
#pragma once
#include <string>
#include <cstdint>
#include <string>
namespace clice {

View File

@@ -2,6 +2,7 @@
#include "AST/SourceCode.h"
#include "Compiler/CompilationUnit.h"
#include "clang/AST/RecursiveASTVisitor.h"
namespace clice {

View File

@@ -1,7 +1,7 @@
#pragma once
#include "clang/AST/Type.h"
#include "clang/AST/ExprCXX.h"
#include "clang/AST/Type.h"
namespace clang {

View File

@@ -1,11 +1,13 @@
#pragma once
#include <stack>
#include "SourceCode.h"
#include "llvm/ADT/SmallVector.h"
#include "clang/AST/ASTTypeTraits.h"
#include "clang/AST/PrettyPrinter.h"
#include "clang/Tooling/Syntax/Tokens.h"
#include "llvm/ADT/SmallVector.h"
namespace clice {
@@ -57,11 +59,11 @@ public:
/// Copies are no good - contain pointers to other nodes.
SelectionTree(const SelectionTree&) = delete;
SelectionTree& operator= (const SelectionTree&) = delete;
SelectionTree& operator=(const SelectionTree&) = delete;
/// Moves are OK though - internal storage is pointer-stable when moved.
SelectionTree(SelectionTree&&) = default;
SelectionTree& operator= (SelectionTree&&) = default;
SelectionTree& operator=(SelectionTree&&) = default;
// Describes to what extent an AST node is covered by the selection.
enum SelectionKind : unsigned char {
@@ -129,7 +131,7 @@ public:
void print(llvm::raw_ostream& os, const Node& node, int indent) const;
friend llvm::raw_ostream& operator<< (llvm::raw_ostream& os, const SelectionTree& tree) {
friend llvm::raw_ostream& operator<<(llvm::raw_ostream& os, const SelectionTree& tree) {
tree.print(os, tree.root(), 1);
return os;
}

View File

@@ -1,10 +1,10 @@
#pragma once
#include "Utility.h"
#include "FilterASTVisitor.h"
#include "RelationKind.h"
#include "Resolver.h"
#include "SymbolKind.h"
#include "RelationKind.h"
#include "FilterASTVisitor.h"
#include "Utility.h"
namespace clice {
@@ -637,7 +637,6 @@ public:
}
bool VisitAttr(clang::Attr* attr) {
getDerived().handleAttrOccurrence(attr, attr->getRange());
return true;
}

View File

@@ -1,8 +1,9 @@
#pragma once
#include <tuple>
#include "clang/Lex/Token.h"
#include "clang/Basic/SourceLocation.h"
#include "clang/Lex/Token.h"
namespace std {
@@ -46,7 +47,7 @@ struct LocalSourceRange {
/// The end position offset to the source file.
uint32_t end = static_cast<uint32_t>(-1);
constexpr bool operator== (const LocalSourceRange& other) const = default;
constexpr bool operator==(const LocalSourceRange& other) const = default;
constexpr auto length() {
return end - begin;
@@ -128,9 +129,9 @@ public:
Lexer(Lexer&&) = delete;
Lexer& operator= (const Lexer&) = delete;
Lexer& operator=(const Lexer&) = delete;
Lexer& operator= (Lexer&&) = delete;
Lexer& operator=(Lexer&&) = delete;
~Lexer();

View File

@@ -1,7 +1,7 @@
#pragma once
#include <string>
#include <cstdint>
#include <string>
namespace clice::index {

View File

@@ -1,6 +1,7 @@
#pragma once
#include "Support/Enum.h"
#include "clang/AST/Decl.h"
namespace clice {

View File

@@ -1,10 +1,10 @@
#pragma once
#include "Lock.h"
#include "Event.h"
#include "Sleep.h"
#include "Gather.h"
#include "Network.h"
#include "FileSystem.h"
#include "Gather.h"
#include "Lock.h"
#include "Network.h"
#include "Sleep.h"
#include "ThreadPool.h"
#include "libuv.h"

View File

@@ -1,6 +1,7 @@
#pragma once
#include "Task.h"
#include "llvm/ADT/ArrayRef.h"
namespace clice::async {

View File

@@ -3,15 +3,14 @@
#include <chrono>
#include <cstddef>
#include "libuv.h"
#include "Task.h"
#include "Awaiter.h"
#include "Support/JSON.h"
#include "Task.h"
#include "libuv.h"
#include "Support/Enum.h"
#include "Support/JSON.h"
#include "llvm/ADT/StringRef.h"
#include "llvm/ADT/FunctionExtras.h"
#include "llvm/ADT/StringRef.h"
namespace clice::async {
@@ -56,9 +55,9 @@ public:
~handle();
handle& operator= (const handle&) = delete;
handle& operator=(const handle&) = delete;
handle& operator= (handle&& other) noexcept = delete;
handle& operator=(handle&& other) noexcept = delete;
int value() const {
return file;

View File

@@ -1,10 +1,10 @@
#pragma once
#include <tuple>
#include <thread>
#include <tuple>
#include "Task.h"
#include "Event.h"
#include "Task.h"
namespace clice::async {

View File

@@ -1,12 +1,11 @@
#pragma once
#include "libuv.h"
#include "Task.h"
#include "libuv.h"
#include "Support/JSON.h"
#include "llvm/ADT/StringRef.h"
#include "llvm/ADT/FunctionExtras.h"
#include "llvm/ADT/StringRef.h"
namespace clice::async::net {

View File

@@ -1,6 +1,7 @@
#pragma once
#include <chrono>
#include "Awaiter.h"
namespace clice::async {

View File

@@ -1,10 +1,10 @@
#pragma once
#include <cassert>
#include <coroutine>
#include <cstdint>
#include <cstdlib>
#include <optional>
#include <coroutine>
#include <source_location>
#include "Support/Format.h"
@@ -247,9 +247,9 @@ public:
other.core = nullptr;
}
Task& operator= (const Task&) = delete;
Task& operator=(const Task&) = delete;
Task& operator= (Task&& other) noexcept {
Task& operator=(Task&& other) noexcept {
if(core) {
core.destroy();
}

View File

@@ -12,11 +12,11 @@
#include <cassert>
#include <expected>
#include <type_traits>
#include <system_error>
#include <type_traits>
#include "Support/TypeTraits.h"
#include "Support/Logging.h"
#include "Support/TypeTraits.h"
namespace clice::async {

View File

@@ -71,9 +71,9 @@ public:
CompilationDatabase(CompilationDatabase&& other);
CompilationDatabase& operator= (const CompilationDatabase&) = delete;
CompilationDatabase& operator=(const CompilationDatabase&) = delete;
CompilationDatabase& operator= (CompilationDatabase&& other);
CompilationDatabase& operator=(CompilationDatabase&& other);
~CompilationDatabase();

View File

@@ -1,12 +1,14 @@
#pragma once
#include "CompilationUnit.h"
#include "Module.h"
#include "Preamble.h"
#include "CompilationUnit.h"
#include "Support/FileSystem.h"
namespace clang {
class CodeCompleteConsumer;
}
namespace clice {

View File

@@ -3,10 +3,11 @@
#include <chrono>
#include "Directive.h"
#include "Compiler/Diagnostic.h"
#include "AST/SymbolID.h"
#include "AST/SourceCode.h"
#include "AST/Resolver.h"
#include "AST/SourceCode.h"
#include "AST/SymbolID.h"
#include "Compiler/Diagnostic.h"
#include "clang/Tooling/Syntax/Tokens.h"
namespace clice {

View File

@@ -9,7 +9,9 @@
#include "clang/Basic/Diagnostic.h"
namespace clang {
class DiagnosticConsumer;
}
namespace clice {

View File

@@ -1,8 +1,9 @@
#pragma once
#include "AST/SourceCode.h"
#include "clang/Lex/MacroInfo.h"
#include "llvm/ADT/DenseMap.h"
#include "clang/Lex/MacroInfo.h"
namespace clice {

View File

@@ -1,8 +1,9 @@
#pragma once
#include <expected>
#include <string>
#include <vector>
#include <expected>
#include "Support/Struct.h"
namespace clice {

View File

@@ -1,8 +1,8 @@
#pragma once
#include <expected>
#include <string>
#include <vector>
#include <expected>
#include "llvm/ADT/StringRef.h"

View File

@@ -2,9 +2,11 @@
#include <string>
#include <vector>
#include "llvm/ADT/StringRef.h"
#include "AST/SourceCode.h"
#include "llvm/ADT/StringRef.h"
namespace clice {
struct Inclusion {

View File

@@ -1,11 +1,13 @@
#pragma once
#include "llvm/ADT/StringRef.h"
#include <memory>
#include "llvm/ADT/StringRef.h"
namespace clang {
class CompilerInstance;
}
namespace clice::tidy {

View File

@@ -1,8 +1,8 @@
#pragma once
#include "llvm/ADT/ArrayRef.h"
#include "llvm/ADT/StringRef.h"
#include "llvm/ADT/STLExtras.h"
#include "llvm/ADT/StringRef.h"
namespace clice::toolchain {

View File

@@ -1,9 +1,10 @@
#pragma once
#include <vector>
#include <cstdint>
#include <vector>
#include "AST/SourceCode.h"
#include "llvm/ADT/StringRef.h"
namespace clice {

View File

@@ -2,6 +2,7 @@
#include "AST/SourceCode.h"
#include "Protocol/Feature/Formatting.h"
#include "llvm/ADT/StringRef.h"
namespace clice::feature {

View File

@@ -1,7 +1,7 @@
#pragma once
#include "AST/SymbolKind.h"
#include "AST/SourceCode.h"
#include "AST/SymbolKind.h"
#include "Index/Shared.h"
namespace clice::config {

View File

@@ -1,7 +1,7 @@
#pragma once
#include "AST/SymbolID.h"
#include "AST/SourceCode.h"
#include "AST/SymbolID.h"
#include "Index/Shared.h"
#include "Support/JSON.h"

View File

@@ -1,8 +1,8 @@
#pragma once
#include "AST/SymbolKind.h"
#include "Server/Protocol.h"
#include "Support/Struct.h"
#include "AST/SymbolKind.h"
namespace clice::proto {

View File

@@ -1,7 +1,7 @@
#pragma once
#include "AST/SymbolKind.h"
#include "AST/SourceCode.h"
#include "AST/SymbolKind.h"
#include "Index/Shared.h"
namespace clice::config {

View File

@@ -1,10 +1,11 @@
#pragma once
#include <vector>
#include <cstdint>
#include <vector>
#include "Protocol/Feature/SignatureHelp.h"
#include "llvm/ADT/StringRef.h"
#include "Protocol/Feature/SignatureHelp.h"
namespace clice {

View File

@@ -1,11 +1,15 @@
#pragma once
#include <vector>
#include "AST/SourceCode.h"
#include "llvm/ADT/DenseMap.h"
namespace clice {
class CompilationUnit;
}
namespace clice::index {
@@ -20,7 +24,7 @@ struct IncludeLocation {
/// The include location that introduces this file.
std::uint32_t include = -1;
friend bool operator== (const IncludeLocation&, const IncludeLocation&) = default;
friend bool operator==(const IncludeLocation&, const IncludeLocation&) = default;
};
struct IncludeGraph {

View File

@@ -1,6 +1,7 @@
#pragma once
#include "TUIndex.h"
#include "llvm/Support/Allocator.h"
#include "llvm/Support/MemoryBuffer.h"
@@ -25,9 +26,9 @@ public:
MergedIndex(MergedIndex&& other);
MergedIndex& operator= (const MergedIndex&) = delete;
MergedIndex& operator=(const MergedIndex&) = delete;
MergedIndex& operator= (MergedIndex&& other);
MergedIndex& operator=(MergedIndex&& other);
~MergedIndex();
@@ -68,7 +69,7 @@ public:
/// Merge the index with given header context.
void merge(this Self& self, std::uint32_t path_id, std::uint32_t include_id, FileIndex& index);
friend bool operator== (MergedIndex& lhs, MergedIndex& rhs);
friend bool operator==(MergedIndex& lhs, MergedIndex& rhs);
private:
/// The binary serialization data of index. If you load merged index

View File

@@ -1,10 +1,11 @@
#pragma once
#include <chrono>
#include "IncludeGraph.h"
#include "AST/RelationKind.h"
#include "AST/SourceCode.h"
#include "AST/SymbolKind.h"
#include "AST/RelationKind.h"
#include "Support/Bitmap.h"
namespace clice::index {
@@ -37,7 +38,7 @@ struct Occurrence {
///
SymbolHash target;
friend bool operator== (const Occurrence&, const Occurrence&) = default;
friend bool operator==(const Occurrence&, const Occurrence&) = default;
};
struct FileIndex {
@@ -56,7 +57,7 @@ struct Symbol {
/// All files that referenced this symbol.
Bitmap reference_files;
friend bool operator== (const Symbol&, const Symbol&) = default;
friend bool operator==(const Symbol&, const Symbol&) = default;
};
using SymbolTable = llvm::DenseMap<SymbolHash, Symbol>;

View File

@@ -1,7 +1,7 @@
#pragma once
#include "clang/AST/Decl.h"
#include "llvm/ADT/SmallVector.h"
#include "clang/AST/Decl.h"
namespace clice::index {

View File

@@ -1,10 +1,10 @@
#pragma once
#include <array>
#include <string>
#include <vector>
#include <cstdint>
#include <optional>
#include <string>
#include <vector>
namespace clice::proto {
@@ -59,7 +59,7 @@ struct Position {
/// `PositionEncodingKind`.
uinteger character;
constexpr friend bool operator== (const Position&, const Position&) = default;
constexpr friend bool operator==(const Position&, const Position&) = default;
};
struct Range {
@@ -69,7 +69,7 @@ struct Range {
/// The range's end position.
Position end;
constexpr friend bool operator== (const Range&, const Range&) = default;
constexpr friend bool operator==(const Range&, const Range&) = default;
};
struct Location {

View File

@@ -1,8 +1,8 @@
#pragma once
#include "Basic.h"
#include "TextDocument.h"
#include "Notebook.h"
#include "TextDocument.h"
#include "Workspace.h"
/// clice currently ignores all `dynamicRegistration` field in LSP specification.

View File

@@ -3,25 +3,25 @@
#include "Basic.h"
#include "Feature/CallHierarchy.h"
#include "Feature/CodeAction.h"
#include "Feature/CodeCompletion.h"
#include "Feature/CodeLens.h"
#include "Feature/Diagnostic.h"
#include "Feature/DocumentLink.h"
#include "Feature/Declaration.h"
#include "Feature/Definition.h"
#include "Feature/Diagnostic.h"
#include "Feature/DocumentHighlight.h"
#include "Feature/DocumentLink.h"
#include "Feature/DocumentSymbol.h"
#include "Feature/FoldingRange.h"
#include "Feature/Formatting.h"
#include "Feature/Hover.h"
#include "Feature/Implementation.h"
#include "Feature/InlayHint.h"
#include "Feature/Reference.h"
#include "Feature/Rename.h"
#include "Feature/SemanticTokens.h"
#include "Feature/SignatureHelp.h"
#include "Feature/Implementation.h"
#include "Feature/CodeCompletion.h"
#include "Feature/TypeDefinition.h"
#include "Feature/TypeHierarchy.h"
#include "Feature/DocumentSymbol.h"
#include "Feature/DocumentHighlight.h"
namespace clice::proto {

View File

@@ -1,7 +1,7 @@
#pragma once
#include <vector>
#include <expected>
#include <vector>
#include "llvm/ADT/ArrayRef.h"
#include "llvm/ADT/StringRef.h"

View File

@@ -1,9 +1,9 @@
#pragma once
#include "Protocol/Protocol.h"
#include "Feature/SemanticToken.h"
#include "Feature/CodeCompletion.h"
#include "Compiler/Diagnostic.h"
#include "Feature/CodeCompletion.h"
#include "Feature/SemanticToken.h"
#include "Protocol/Protocol.h"
#include "Support/FileSystem.h"
#include "Support/JSON.h"

View File

@@ -5,7 +5,6 @@
#include "Config.h"
#include "Convert.h"
#include "Async/Async.h"
#include "Compiler/Command.h"
#include "Index/MergedIndex.h"

View File

@@ -5,8 +5,8 @@
#include "Indexer.h"
#include "Async/Async.h"
#include "Compiler/Command.h"
#include "Compiler/Preamble.h"
#include "Compiler/Diagnostic.h"
#include "Compiler/Preamble.h"
#include "Feature/DocumentLink.h"
#include "Protocol/Protocol.h"
@@ -61,7 +61,7 @@ public:
ActiveFileManager() : capability(DefaultMaxActiveFileNum) {}
ActiveFileManager(const ActiveFileManager&) = delete;
ActiveFileManager& operator= (const ActiveFileManager&) = delete;
ActiveFileManager& operator=(const ActiveFileManager&) = delete;
/// Set the maximum active file count and it will be clamped to [1, UnlimitedActiveFileNum].
void set_capability(size_t size) {

View File

@@ -1,14 +1,14 @@
#pragma once
#include <vector>
#include <cstdint>
#include <cstring>
#include <cstdlib>
#include <cstring>
#include <vector>
#include "Enum.h"
#include "Struct.h"
#include "Format.h"
#include "FixedString.h"
#include "Format.h"
#include "Struct.h"
#include "llvm/ADT/ArrayRef.h"
#include "llvm/ADT/StringRef.h"
@@ -263,7 +263,7 @@ struct Proxy {
};
}
auto operator[] (std::size_t index) const {
auto operator[](std::size_t index) const {
return Proxy<typename T::value_type>{base, &as_array()[index]};
}

View File

@@ -16,7 +16,7 @@ struct Equal {
struct equal_t {
template <typename LHS, typename RHS = LHS>
constexpr static bool operator() (const LHS& lhs, const RHS& rhs) {
constexpr static bool operator()(const LHS& lhs, const RHS& rhs) {
return Equal<LHS, RHS>::equal(lhs, rhs);
}
};
@@ -68,7 +68,7 @@ struct Less {
struct less_t {
template <typename RHS, typename LHS = RHS>
constexpr static bool operator() (const LHS& lhs, const RHS& rhs) {
constexpr static bool operator()(const LHS& lhs, const RHS& rhs) {
return Less<RHS, LHS>::less(lhs, rhs);
}
};
@@ -127,7 +127,7 @@ struct Less<T> {
struct less_equal_t {
template <typename LHS, typename RHS = LHS>
constexpr static bool operator() (const LHS& lhs, const RHS& rhs) {
constexpr static bool operator()(const LHS& lhs, const RHS& rhs) {
return equal(lhs, rhs) || less(lhs, rhs);
}
};

View File

@@ -1,11 +1,11 @@
#pragma once
#include <string>
#include <memory>
#include <string>
#include "llvm/ADT/StringRef.h"
#include "llvm/ADT/DenseMap.h"
#include "llvm/ADT/ArrayRef.h"
#include "llvm/ADT/DenseMap.h"
#include "llvm/ADT/StringRef.h"
namespace clice {

View File

@@ -1,12 +1,12 @@
#pragma once
#include <bit>
#include <array>
#include <string>
#include <cstdint>
#include <bit>
#include <cassert>
#include <string_view>
#include <cstdint>
#include <source_location>
#include <string>
#include <string_view>
#include "Support/TypeTraits.h"
@@ -81,7 +81,7 @@ public:
constexpr Enum(const Enum&) = default;
constexpr Enum& operator= (const Enum&) = default;
constexpr Enum& operator=(const Enum&) = default;
/// Get the underlying value of the enum.
constexpr underlying value() const {
@@ -108,7 +108,7 @@ public:
return m_Value != invalid();
}
constexpr friend bool operator== (Enum lhs, Enum rhs) = default;
constexpr friend bool operator==(Enum lhs, Enum rhs) = default;
constexpr static auto& all() {
return enum_table<typename Derived::Kind, end() - begin()>::table;
@@ -165,7 +165,7 @@ public:
constexpr Enum(const Enum&) = default;
constexpr Enum& operator= (const Enum&) = default;
constexpr Enum& operator=(const Enum&) = default;
/// Get the underlying value of the enum.
constexpr underlying value() const {
@@ -203,30 +203,30 @@ public:
return m_Value != 0;
}
constexpr friend bool operator== (Enum lhs, Enum rhs) = default;
constexpr friend bool operator==(Enum lhs, Enum rhs) = default;
template <std::same_as<typename Derived::Kind> Kind>
constexpr Enum operator| (Kind kind) const {
constexpr Enum operator|(Kind kind) const {
return Enum(m_Value | (1 << underlying_value(kind)));
}
template <std::same_as<typename Derived::Kind> Kind>
constexpr Enum operator& (Kind kind) const {
constexpr Enum operator&(Kind kind) const {
return Enum(m_Value & (1 << underlying_value(kind)));
}
constexpr Enum operator& (Enum e) const {
constexpr Enum operator&(Enum e) const {
return Enum(m_Value & e.value());
}
template <std::same_as<typename Derived::Kind> Kind>
constexpr Enum& operator|= (Kind kind) {
constexpr Enum& operator|=(Kind kind) {
m_Value |= (1 << underlying_value(kind));
return *this;
}
template <std::same_as<typename Derived::Kind> Kind>
constexpr Enum& operator&= (Kind kind) {
constexpr Enum& operator&=(Kind kind) {
m_Value &= (1 << underlying_value(kind));
return *this;
}
@@ -282,7 +282,7 @@ public:
constexpr Enum(const Enum&) = default;
constexpr friend bool operator== (Enum lhs, Enum rhs) = default;
constexpr friend bool operator==(Enum lhs, Enum rhs) = default;
constexpr underlying value() const {
return m_Value;

View File

@@ -3,11 +3,12 @@
#include <expected>
#include "Assert.h"
#include "llvm/Support/Path.h"
#include "llvm/Support/FileSystem.h"
#include "llvm/Support/VirtualFileSystem.h"
#include "llvm/Support/MemoryBuffer.h"
#include "llvm/ADT/StringExtras.h"
#include "llvm/Support/FileSystem.h"
#include "llvm/Support/MemoryBuffer.h"
#include "llvm/Support/Path.h"
#include "llvm/Support/VirtualFileSystem.h"
namespace clice {

View File

@@ -15,6 +15,13 @@ struct fixed_string : std::array<char, N + 1> {
this->data()[N] = '\0';
}
constexpr fixed_string(const char* str) {
for(std::size_t i = 0; i < N; ++i) {
this->data()[i] = str[i];
}
this->data()[N] = '\0';
}
constexpr auto size() const {
return N;
}

View File

@@ -2,8 +2,10 @@
#include <format>
#include <print>
#include "Support/JSON.h"
#include "Support/Ranges.h"
#include "llvm/Support/Error.h"
template <>

View File

@@ -1,6 +1,7 @@
#pragma once
#include <optional>
#include "llvm/ADT/ArrayRef.h"
#include "llvm/ADT/SmallString.h"
#include "llvm/ADT/StringRef.h"

View File

@@ -1,8 +1,8 @@
#pragma once
#include <bitset>
#include <expected>
#include <string>
#include <bitset>
#include "llvm/ADT/STLExtras.h"
#include "llvm/ADT/SmallVector.h"

View File

@@ -1,6 +1,7 @@
#pragma once
#include "Struct.h"
#include "llvm/Support/HashBuilder.h"
namespace clice::refl {

View File

@@ -1,14 +1,14 @@
#pragma once
#include <array>
#include <vector>
#include <ranges>
#include <string_view>
#include <vector>
#include "Ranges.h"
#include "TypeTraits.h"
#include "Enum.h"
#include "Ranges.h"
#include "Struct.h"
#include "TypeTraits.h"
#include "llvm/Support/JSON.h"

View File

@@ -1,6 +1,7 @@
#pragma once
#include "Format.h"
#include "spdlog/spdlog.h"
namespace clice::logging {

View File

@@ -1,7 +1,7 @@
#pragma once
#include "llvm/ADT/StringRef.h"
#include "llvm/ADT/DenseMap.h"
#include "llvm/ADT/StringRef.h"
#include "llvm/Support/Allocator.h"
namespace clice {
@@ -18,9 +18,9 @@ public:
StringSet(StringSet&&) = delete;
StringSet& operator= (const StringSet&) = delete;
StringSet& operator=(const StringSet&) = delete;
StringSet& operator= (StringSet&&) = delete;
StringSet& operator=(StringSet&&) = delete;
~StringSet() = default;
@@ -72,7 +72,7 @@ struct object_ptr {
explicit object_ptr(T* p) noexcept : ptr(p) {}
T& operator* () const noexcept {
T& operator*() const noexcept {
return *ptr;
}
@@ -84,7 +84,7 @@ struct object_ptr {
return ptr != nullptr;
}
std::strong_ordering operator<=> (const object_ptr&) const = default;
std::strong_ordering operator<=>(const object_ptr&) const = default;
};
template <typename T>
@@ -101,9 +101,9 @@ public:
ObjectSet(ObjectSet&&) = delete;
ObjectSet& operator= (const ObjectSet&) = delete;
ObjectSet& operator=(const ObjectSet&) = delete;
ObjectSet& operator= (ObjectSet&&) = delete;
ObjectSet& operator=(ObjectSet&&) = delete;
~ObjectSet() {
if constexpr(!std::is_trivially_destructible_v<T>) {

View File

@@ -1,7 +1,7 @@
#pragma once
#include <ranges>
#include <concepts>
#include <ranges>
namespace clice {

View File

@@ -1,9 +1,9 @@
#pragma once
#include <tuple>
#include <array>
#include <string_view>
#include <source_location>
#include <string_view>
#include <tuple>
#include "Support/TypeTraits.h"

View File

@@ -76,7 +76,7 @@ public:
StructedText(StructedText&&) = default;
StructedText& operator= (const StructedText& other) {
StructedText& operator=(const StructedText& other) {
blocks.clear();
for(auto& b: other.blocks) {
blocks.push_back(b->clone());
@@ -84,7 +84,7 @@ public:
return *this;
}
StructedText& operator= (StructedText&&) = default;
StructedText& operator=(StructedText&&) = default;
void append(StructedText& doc);

View File

@@ -1,8 +1,9 @@
#pragma once
#include "AST/SourceCode.h"
#include "llvm/ADT/StringRef.h"
#include "llvm/ADT/StringMap.h"
#include "llvm/ADT/StringRef.h"
namespace clice::testing {
@@ -23,123 +24,7 @@ struct AnnotatedSource {
///
/// A range annotation for 'key' creates both a `ranges["key"]` and an `offsets["key"]`
/// (pointing to the start).
static AnnotatedSource from(llvm::StringRef content) {
std::string source;
source.reserve(content.size());
llvm::StringMap<std::uint32_t> offsets;
llvm::StringMap<LocalSourceRange> ranges;
std::vector<std::uint32_t> nameless_offsets;
std::uint32_t offset = 0;
std::uint32_t i = 0;
// Helper lambda to parse a point annotation $(key).
// It captures all necessary variables by reference.
// Returns true if a point was successfully parsed, false otherwise.
auto try_parse_point_annotation = [&]() -> bool {
if(content[i] != '$') {
return false;
}
// Peek ahead to see if it's "$(key)" or just "$"
if(i + 1 < content.size() && content[i + 1] == '(') {
// It's the full "$(key)" syntax
uint32_t key_start = i + 2;
size_t key_end = content.find(')', key_start);
if(key_end == llvm::StringRef::npos) {
return false;
} // Malformed
llvm::StringRef key = content.slice(key_start, key_end);
/// empty key is regarded as a nameless, and `()` is not consumed.
if(key.empty()) {
// It's the shorthand "$" syntax for an nameless key
nameless_offsets.emplace_back(offset);
i += 1; // Advance cursor past the single '$'
} else {
offsets.try_emplace(key, offset);
i = key_end + 1; // Advance cursor past the entire "$(key)"
}
return true;
} else {
// It's the shorthand "$" syntax for an nameless key
nameless_offsets.emplace_back(offset);
i += 1; // Advance cursor past the single '$'
return true;
}
};
while(i < content.size()) {
// Check for a point annotation first.
if(try_parse_point_annotation()) {
continue;
}
char c = content[i];
// Handle Range: @key[...]
if(c == '@') {
// Skip '@'
i += 1;
const char open_bracket = '[';
const char close_bracket = ']';
llvm::StringRef key = content.substr(i).take_until(
[&](char c) { return isspace(c) || c == open_bracket; });
i += key.size();
while(i < content.size() && isspace(content[i])) {
i++;
}
assert(i < content.size() && content[i] == open_bracket &&
"Expect @key[...] for ranges.");
i += 1; // Skip '['
uint32_t begin_offset = offset;
int bracket_level = 1;
while(i < content.size() && bracket_level > 0) {
// Inside a range, we can still have nested point annotations.
if(try_parse_point_annotation()) {
continue;
}
char inner_c = content[i];
if(inner_c == open_bracket)
bracket_level++;
else if(inner_c == close_bracket)
bracket_level--;
if(bracket_level > 0) {
source += inner_c;
offset += 1;
i += 1;
} else {
i += 1; // Skip the final ']'
}
}
ranges.try_emplace(key, LocalSourceRange{begin_offset, offset});
continue;
}
// If nothing else matched, it's a regular character.
source += c;
offset += 1;
i += 1;
}
return AnnotatedSource{
std::move(source),
std::move(offsets),
std::move(ranges),
std::move(nameless_offsets),
};
}
static AnnotatedSource from(llvm::StringRef content);
};
struct AnnotatedSources {
@@ -161,41 +46,7 @@ struct AnnotatedSources {
/// #include "test.h"
/// int x = foo();
/// ```
void add_sources(llvm::StringRef content) {
std::string curr_file;
std::string curr_content;
/// Save previous file to params.
auto save_previous_file = [&]() {
if(curr_file.empty()) {
return;
}
add_source(curr_file, curr_content);
curr_file.clear();
curr_content.clear();
};
while(!content.empty()) {
llvm::StringRef line = content.take_front(content.find_first_of("\r\n"));
content = content.drop_front(line.size());
if(content.starts_with("\r\n")) {
content = content.drop_front(2);
} else if(content.starts_with("\n")) {
content = content.drop_front(1);
}
if(line.starts_with("#[") && line.ends_with("]")) {
save_previous_file();
curr_file = line.slice(2, line.size() - 1).str();
} else if(!curr_file.empty()) {
curr_content += line;
curr_content += '\n';
}
}
save_previous_file();
}
void add_sources(llvm::StringRef content);
};
} // namespace clice::testing

View File

@@ -1,34 +0,0 @@
#pragma once
#include <vector>
#include <iostream>
#include <source_location>
namespace clice::testing {
struct LocationChain {
/// All positions in the call chain, with the later
/// ones representing deeper inner levels.
std::vector<std::source_location> locations;
LocationChain(std::source_location current = std::source_location::current()) :
locations{current} {}
LocationChain(LocationChain& outer,
std::source_location current = std::source_location::current()) :
locations{outer.locations} {
locations.emplace_back(current);
}
LocationChain(const LocationChain&) = delete;
/// Dump all locations.
void backtrace() {
for(auto location: locations) {
std::cout << location.file_name() << ":" << location.line() << ":" << location.column()
<< "\n";
}
}
};
} // namespace clice::testing

View File

@@ -1,4 +1,3 @@
namespace clice::testing {
/// True if the target platform is Windows.
@@ -48,4 +47,5 @@ constexpr inline bool CIEnvironment = true;
#else
constexpr inline bool CIEnvironment = false;
#endif
} // namespace clice::testing

49
include/Test/Runner.h Normal file
View File

@@ -0,0 +1,49 @@
#pragma once
#include <source_location>
#include <string>
#include <vector>
#include "llvm/ADT/FunctionExtras.h"
#include "llvm/ADT/StringRef.h"
namespace clice::testing {
enum class TestState {
Passed,
Skipped,
Failed,
Fatal,
};
struct TestAttrs {
bool skip = false;
bool focus = false;
};
struct TestCase {
std::string name;
std::string path;
std::size_t line;
TestAttrs attrs;
llvm::unique_function<TestState()> test;
};
struct TestSuite {
std::string name;
std::vector<TestCase> (*cases)();
};
class Runner2 {
public:
static Runner2& instance();
void add_suite(std::string_view suite, std::vector<TestCase> (*cases)());
int run_tests(llvm::StringRef filter);
private:
std::vector<TestSuite> suites;
};
} // namespace clice::testing

View File

@@ -1,110 +0,0 @@
#pragma once
#include <string>
#include <format>
#include <algorithm>
#include <functional>
#include "Support/Compare.h"
#include "Support/Ranges.h"
#include "llvm/ADT/SmallString.h"
#include "llvm/Support/raw_ostream.h"
namespace clice::testing {
template <typename T>
concept is_expr_v = requires { typename T::expr_tag; };
template <typename Derived>
struct default_formatter : std::formatter<std::string_view> {
using Base = std::formatter<std::string_view>;
template <typename FormatContext>
auto format(const auto& value, FormatContext& ctx) const {
llvm::SmallString<256> buffer;
static_cast<const Derived*>(this)->format_to(std::back_inserter(buffer), value);
return Base::format(std::string_view(buffer), ctx);
}
};
template <typename Expr>
decltype(auto) compute(const Expr& expr) {
if constexpr(requires { typename Expr::expr_tag; }) {
return expr();
} else {
return expr;
}
}
} // namespace clice::testing
#define BINARY_PREDICATE(name, op) \
namespace clice::testing { \
decltype(auto) name##_impl(auto&& lhs, auto&& rhs); \
\
template <typename LHS, typename RHS> \
struct name { \
const LHS& lhs; \
const RHS& rhs; \
\
using expr_tag = int; \
\
auto operator() () const { \
return name##_impl(compute(lhs), compute(rhs)); \
} \
}; \
\
template <typename LHS, typename RHS> \
name(const LHS&, const RHS&) -> name<LHS, RHS>; \
} \
\
template <typename LHS, typename RHS> \
struct std::formatter<clice::testing::name<LHS, RHS>> : \
clice::testing::default_formatter<std::formatter<clice::testing::name<LHS, RHS>>> { \
void format_to(auto&& inserter, const auto& expr) const { \
std::format_to(inserter, "{} " #op " {}", expr.lhs, expr.rhs); \
} \
}; \
\
decltype(auto) clice::testing::name##_impl(auto&& lhs, auto&& rhs)
BINARY_PREDICATE(add, +) {
return lhs + rhs;
};
BINARY_PREDICATE(sub, -) {
return lhs - rhs;
}
BINARY_PREDICATE(mul, *) {
return lhs * rhs;
}
BINARY_PREDICATE(eq, ==) {
return refl::equal(lhs, rhs);
}
BINARY_PREDICATE(ne, !=) {
return !refl::equal(lhs, rhs);
}
BINARY_PREDICATE(lt, <) {
return refl::less(lhs, rhs);
}
BINARY_PREDICATE(le, <=) {
return refl::less_equal(lhs, rhs);
}
BINARY_PREDICATE(gt, >) {
return refl::less(rhs, lhs);
}
BINARY_PREDICATE(ge, >=) {
return refl::less_equal(rhs, lhs);
}
BINARY_PREDICATE(has, has) {
return ranges::contains(lhs, rhs);
}
#undef BINARY_PREDICATE

View File

@@ -1,179 +1,130 @@
#pragma once
#include "TExpr.h"
#include <print>
#include <source_location>
#include <string>
#include <vector>
#include "Platform.h"
#include "LocationChain.h"
#include "Support/JSON.h"
#include "Support/Format.h"
#include "Runner.h"
#include "Support/Compare.h"
#include "Support/FileSystem.h"
#include "Support/FixedString.h"
#include "cpptrace/cpptrace.hpp"
#include "llvm/ADT/FunctionExtras.h"
#include "llvm/ADT/StringMap.h"
namespace clice::testing {
struct may_failure;
template <fixed_string TestName, typename Derived>
struct TestSuiteDef {
private:
TestState state = TestState::Passed;
class Runner {
public:
static Runner& instance();
using Self = Derived;
using Suite = void (*)();
using Test = llvm::unique_function<void()>;
void add_suite(std::string_view name, Suite suite);
void on_test(std::string_view name, Test test, bool skipped);
/// Current test is failed, continue to execute the next test in the suite.
void fail(const may_failure& failure);
bool fatal_error_occured() {
return curr_fatal;
void failure() {
state = TestState::Failed;
}
/// Run all test suites.
int run_tests();
private:
Runner() = default;
Runner(const Runner&) = delete;
Runner(Runner&&) = delete;
private:
bool curr_failed = false;
bool skipped = false;
bool curr_fatal = false;
/// Whether all tests in this test suite are skipped.
bool all_skipped = true;
std::string curr_suite_name;
std::uint32_t curr_tests_count = 0;
std::uint32_t curr_failed_tests_count = 0;
std::uint32_t total_tests_count = 0;
std::uint32_t total_suites_count = 0;
std::uint32_t total_failed_tests_count = 0;
std::chrono::milliseconds curr_test_duration;
std::chrono::milliseconds total_test_duration;
std::unordered_map<std::string_view, std::vector<Suite>> suites;
};
template <fixed_string suite_name>
struct suite {
template <typename Suite>
suite(Suite suite) {
static_assert(std::convertible_to<Suite, Runner::Suite>, "Suite must be stateless!");
Runner::instance().add_suite(suite_name, suite);
}
};
struct test {
test(std::string_view name) : name(name) {}
template <typename Test>
void operator= (Test&& test) {
Runner::instance().on_test(name, std::forward<Test>(test), skipped);
void pass() {
state = TestState::Passed;
}
bool skipped = false;
std::string name;
};
struct may_failure {
bool failed = false;
bool fatal = false;
std::string expression;
std::source_location location;
std::string message;
may_failure& operator<< (std::string message) {
this->message += std::move(message);
return *this;
void skip() {
state = TestState::Skipped;
}
~may_failure() {
Runner::instance().fail(*this);
constexpr inline static auto& test_cases() {
static std::vector<TestCase> instance;
return instance;
}
};
constexpr inline struct {
template <typename TExpr>
may_failure operator() (const TExpr& expr,
std::source_location location = std::source_location::current()) const {
bool failed = false;
std::string expression = "false";
std::string message;
constexpr inline static auto suites() {
return std::move(test_cases());
}
if constexpr(is_expr_v<TExpr>) {
auto result = expr();
if(!static_cast<bool>(result)) {
failed = true;
template <typename T = void>
inline static bool _register_suites = [] {
Runner2::instance().add_suite(TestName.data(), &suites);
return true;
}();
/// TODO: use pretty print, if the expression is too long.
expression = std::format("{}", expr);
template <fixed_string case_name,
auto test_body,
fixed_string path,
std::size_t line,
TestAttrs attrs = {}>
inline static bool _register_test_case = [] {
auto run_test = +[] -> TestState {
Derived test;
if constexpr(requires { test.setup(); }) {
test.setup();
}
} else {
if(!static_cast<bool>(expr)) {
failed = true;
if constexpr(requires { expr.error(); }) {
message = std::format("{}", expr.error());
}
(test.*test_body)();
if constexpr(requires { test.teardown(); }) {
test.teardown();
}
}
return may_failure{
failed,
false,
std::move(expression),
location,
std::move(message),
return test.state;
};
}
} expect;
constexpr inline struct {
test&& operator/ (test&& test) const {
test.skipped = true;
return std::move(test);
}
} skip;
struct skip_if {
bool condition;
test&& operator/ (test&& test) const {
test.skipped = condition;
return std::move(test);
}
test_cases().emplace_back(case_name.data(), path.data(), line, attrs, run_test);
return true;
}();
};
struct skip_unless {
bool condition;
inline void print_trace(cpptrace::stacktrace& trace, std::source_location location) {
auto& frames = trace.frames;
auto it = std::ranges::find_if(frames, [&](cpptrace::stacktrace_frame& frame) {
return frame.filename != location.file_name();
});
frames.erase(it, frames.end());
trace.print();
}
test&& operator/ (test&& test) const {
test.skipped = !condition;
return std::move(test);
}
};
#define TEST_SUITE(name) struct name##TEST : TestSuiteDef<#name, name##TEST>
constexpr inline struct {
may_failure&& operator/ (may_failure&& failure) const {
if(failure.failed) {
failure.fatal = true;
}
return std::move(failure);
}
} fatal;
#define TEST_CASE(name, ...) \
void _register_##name() { \
constexpr auto file_name = std::source_location::current().file_name(); \
constexpr auto file_len = std::string_view(file_name).size(); \
(void)_register_suites<>; \
(void)_register_test_case<#name, \
&Self::test_##name, \
fixed_string<file_len>(file_name), \
std::source_location::current().line() __VA_OPT__(, ) \
__VA_ARGS__>; \
} \
void test_##name()
struct that_t {
template <typename TExpr>
constexpr decltype(auto) operator% (const TExpr& expr) const {
return expr;
}
};
#define CLICE_CHECK_IMPL(condition, return_action) \
do { \
if(condition) [[unlikely]] { \
auto trace = cpptrace::generate_trace(); \
clice::testing::print_trace(trace, std::source_location::current()); \
failure(); \
return_action; \
} \
} while(0)
inline that_t that;
#define EXPECT_TRUE(expr) CLICE_CHECK_IMPL(!(expr), (void)0)
#define EXPECT_FALSE(expr) CLICE_CHECK_IMPL((expr), (void)0)
#define EXPECT_EQ(lhs, rhs) CLICE_CHECK_IMPL((lhs) != (rhs), (void)0)
#define EXPECT_NE(lhs, rhs) CLICE_CHECK_IMPL((lhs) == (rhs), (void)0)
#define ASSERT_TRUE(expr) CLICE_CHECK_IMPL(!(expr), return)
#define ASSERT_FALSE(expr) CLICE_CHECK_IMPL((expr), return)
#define ASSERT_EQ(lhs, rhs) CLICE_CHECK_IMPL((lhs) != (rhs), return)
#define ASSERT_NE(lhs, rhs) CLICE_CHECK_IMPL((lhs) == (rhs), return)
#define CO_ASSERT_TRUE(expr) CLICE_CHECK_IMPL(!(expr), co_return)
#define CO_ASSERT_FALSE(expr) CLICE_CHECK_IMPL((expr), co_return)
#define CO_ASSERT_EQ(lhs, rhs) CLICE_CHECK_IMPL((lhs) != (rhs), co_return)
#define CO_ASSERT_NE(lhs, rhs) CLICE_CHECK_IMPL((lhs) == (rhs), co_return)
} // namespace clice::testing

View File

@@ -1,10 +1,10 @@
#pragma once
#include "Test.h"
#include "Annotation.h"
#include "Protocol/Protocol.h"
#include "Test.h"
#include "Compiler/Command.h"
#include "Compiler/Compilation.h"
#include "Protocol/Protocol.h"
#include "Support/Logging.h"
namespace clice::testing {
@@ -38,7 +38,7 @@ struct Tester {
bool compile_with_pch(llvm::StringRef standard = "-std=c++20");
std::uint32_t operator[] (llvm::StringRef file, llvm::StringRef pos) {
std::uint32_t operator[](llvm::StringRef file, llvm::StringRef pos) {
return sources.all_files.lookup(file).offsets.lookup(pos);
}

View File

@@ -1,8 +1,10 @@
#include "AST/Resolver.h"
#include "Support/Format.h"
#include "clang/Sema/Template.h"
#include "clang/Sema/TreeTransform.h"
#include "clang/Sema/TemplateDeduction.h"
#include "clang/Sema/TreeTransform.h"
namespace clice {
@@ -626,10 +628,14 @@ public:
/// SomeAllocator<U, Args> -> SomeAllocator<T, Args>
if(auto TST = Alloc->getAs<clang::TemplateSpecializationType>()) {
llvm::SmallVector<clang::TemplateArgument, 4> replaceArguments = {T};
llvm::SmallVector<clang::TemplateArgument, 1> replaceArguments = {T};
llvm::SmallVector<clang::TemplateArgument, 1> canonicalArguments;
for(auto& arg: replaceArguments) {
canonicalArguments.emplace_back(context.getCanonicalTemplateArgument(arg));
}
return context.getTemplateSpecializationType(TST->getTemplateName(),
replaceArguments,
replaceArguments);
canonicalArguments);
}
}
}

View File

@@ -1,10 +1,13 @@
#include "AST/Selection.h"
#include <algorithm>
#include <optional>
#include <set>
#include <string>
#include <optional>
#include <algorithm>
#include "AST/Selection.h"
#include "Compiler/CompilationUnit.h"
#include "Support/Logging.h"
#include "llvm/ADT/BitVector.h"
#include "llvm/ADT/STLExtras.h"
#include "llvm/ADT/StringExtras.h"
@@ -193,7 +196,7 @@ public:
private:
struct range_less {
bool operator() (TokenRange L, TokenRange R) const {
bool operator()(TokenRange L, TokenRange R) const {
return L.begin() < R.begin();
}
};

View File

@@ -1,4 +1,5 @@
#include "AST/SymbolKind.h"
#include "Compiler/Compilation.h"
namespace clice {

View File

@@ -1,18 +1,20 @@
#include "AST/Utility.h"
#include "Support/Format.h"
#include "llvm/ADT/STLExtras.h"
#include "llvm/ADT/SmallSet.h"
#include "llvm/Support/SaveAndRestore.h"
#include "llvm/Support/ScopedPrinter.h"
#include "clang/AST/ASTDiagnostic.h"
#include "clang/AST/Decl.h"
#include "clang/AST/DeclCXX.h"
#include "clang/AST/DeclObjC.h"
#include "clang/AST/DeclTemplate.h"
#include "clang/AST/RecursiveASTVisitor.h"
#include "clang/AST/StmtVisitor.h"
#include "clang/AST/Type.h"
#include "clang/Basic/SourceManager.h"
#include "clang/AST/StmtVisitor.h"
#include "clang/AST/RecursiveASTVisitor.h"
#include "llvm/ADT/STLExtras.h"
#include "llvm/Support/SaveAndRestore.h"
#include "llvm/Support/ScopedPrinter.h"
#include "llvm/ADT/SmallSet.h"
#include "clang/AST/ASTDiagnostic.h"
namespace clice::ast {
@@ -98,7 +100,6 @@ const static clang::CXXRecordDecl* getDeclContextForTemplateInstationPattern(con
const clang::NamedDecl* instantiated_from(const clang::NamedDecl* decl) {
if(auto CTSD = llvm::dyn_cast<clang::ClassTemplateSpecializationDecl>(decl)) {
auto kind = CTSD->getTemplateSpecializationKind();
if(kind == clang::TSK_Undeclared) {
/// The instantiation of template is lazy, in this case, the specialization is

View File

@@ -1,7 +1,7 @@
#include <deque>
#include "Async/Async.h"
#include <deque>
namespace clice::async {
/// The default event loop.

View File

@@ -1,4 +1,5 @@
#include "Async/FileSystem.h"
#include "Support/Logging.h"
namespace clice::async::awaiter {}

View File

@@ -1,4 +1,5 @@
#include "Async/Network.h"
#include "Support/Logging.h"
namespace clice::async::net {

View File

@@ -1,11 +1,13 @@
#include "Compiler/Command.h"
#include "Driver.h"
#include "Compiler/Compilation.h"
#include "Support/FileSystem.h"
#include "Support/Logging.h"
#include "Support/ObjectPool.h"
#include "llvm/ADT/ScopeExit.h"
#include "llvm/Support/CommandLine.h"
#include "Driver.h"
#include "Support/ObjectPool.h"
namespace clice {
@@ -20,7 +22,7 @@ struct CompilationInfo {
/// The canonical compilation arguments(input file and output file are removed).
llvm::ArrayRef<StringID> arguments;
friend bool operator== (const CompilationInfo&, const CompilationInfo&) = default;
friend bool operator==(const CompilationInfo&, const CompilationInfo&) = default;
};
/// An item in the compilation database.
@@ -40,12 +42,12 @@ struct JSONItem {
/// get involved in equality judgement or hash computing.
object_ptr<JSONItem> next = {nullptr};
friend bool operator== (const JSONItem& lhs, const JSONItem& rhs) {
friend bool operator==(const JSONItem& lhs, const JSONItem& rhs) {
return lhs.json_src_path == rhs.json_src_path && lhs.file_path == rhs.file_path &&
lhs.info == rhs.info;
}
friend bool operator< (const JSONItem& lhs, const JSONItem& rhs) {
friend bool operator<(const JSONItem& lhs, const JSONItem& rhs) {
return std::tie(lhs.file_path, lhs.info) < std::tie(rhs.file_path, rhs.info);
}
};
@@ -564,7 +566,7 @@ CompilationDatabase::CompilationDatabase() : self(std::make_unique<CompilationDa
CompilationDatabase::CompilationDatabase(CompilationDatabase&& other) = default;
CompilationDatabase& CompilationDatabase::operator= (CompilationDatabase&& other) = default;
CompilationDatabase& CompilationDatabase::operator=(CompilationDatabase&& other) = default;
CompilationDatabase::~CompilationDatabase() = default;

View File

@@ -1,17 +1,17 @@
#include "TidyImpl.h"
#include "AST/Utility.h"
#include "CompilationUnitImpl.h"
#include "Compiler/Command.h"
#include "Compiler/Compilation.h"
#include "CompilationUnitImpl.h"
#include "TidyImpl.h"
#include "AST/Utility.h"
#include "Compiler/Command.h"
#include "Compiler/Diagnostic.h"
#include "Compiler/Tidy.h"
#include "clang/Lex/PreprocessorOptions.h"
#include "clang/Frontend/TextDiagnosticPrinter.h"
#include "clang/Frontend/MultiplexConsumer.h"
#include "Support/Logging.h"
#include "clang/Frontend/MultiplexConsumer.h"
#include "clang/Frontend/TextDiagnosticPrinter.h"
#include "clang/Lex/PreprocessorOptions.h"
namespace clice {
namespace {

View File

@@ -1,6 +1,6 @@
#include "CompilationUnitImpl.h"
#include "Index/USR.h"
#include "AST/Utility.h"
#include "Index/USR.h"
namespace clice {

View File

@@ -2,8 +2,9 @@
#include "Compiler/CompilationUnit.h"
#include "Compiler/Diagnostic.h"
#include "clang/Frontend/FrontendActions.h"
#include "clang/Frontend/CompilerInstance.h"
#include "clang/Frontend/FrontendActions.h"
namespace clice {

View File

@@ -1,13 +1,14 @@
#include "Compiler/Diagnostic.h"
#include "Support/Format.h"
#include "TidyImpl.h"
#include "clang/AST/Type.h"
#include "TidyImpl.h"
#include "Support/Format.h"
#include "clang/AST/Decl.h"
#include "clang/AST/DeclCXX.h"
#include "clang/AST/Type.h"
#include "clang/Basic/AllDiagnostics.h"
#include "clang/Basic/Diagnostic.h"
#include "clang/Basic/DiagnosticIDs.h"
#include "clang/Basic/AllDiagnostics.h"
#include "clang/Basic/SourceManager.h"
#include "clang/Lex/Preprocessor.h"
@@ -212,7 +213,6 @@ public:
void HandleDiagnostic(clang::DiagnosticsEngine::Level level,
const clang::Diagnostic& raw_diagnostic) override {
auto& diagnostic = diagnostics->emplace_back();
diagnostic.id.value = raw_diagnostic.getID();

View File

@@ -1,6 +1,7 @@
#include "Compiler/Directive.h"
#include "clang/Lex/MacroInfo.h"
#include "clang/Lex/MacroArgs.h"
#include "clang/Lex/MacroInfo.h"
#include "clang/Lex/Preprocessor.h"
namespace clice {

View File

@@ -2,10 +2,11 @@
#include "Compiler/Command.h"
#include "Support/Logging.h"
#include "llvm/ADT/ScopeExit.h"
#include "llvm/Support/FileSystem.h"
#include "llvm/Support/Path.h"
#include "llvm/Support/Program.h"
#include "llvm/Support/FileSystem.h"
#include "clang/Driver/Driver.h"
namespace clice {

View File

@@ -1,5 +1,7 @@
#include "Compiler/Module.h"
#include "Compiler/Compilation.h"
#include "clang/Lex/Lexer.h"
namespace clice {

View File

@@ -1,4 +1,5 @@
#include "Compiler/Preamble.h"
#include "AST/SourceCode.h"
#include "Support/Format.h"
#include "Support/Logging.h"

View File

@@ -10,21 +10,23 @@
/// https://github.com/llvm/llvm-project//blob/0865ecc5150b9a55ba1f9e30b6d463a66ac362a6/clang-tools-extra/clangd/ParsedAST.cpp#L547
/// https://github.com/llvm/llvm-project//blob/0865ecc5150b9a55ba1f9e30b6d463a66ac362a6/clang-tools-extra/clangd/TidyProvider.cpp
#include "Compiler/Tidy.h"
#include "TidyImpl.h"
#include "AST/Utility.h"
#include "Compiler/Diagnostic.h"
#include "Compiler/Tidy.h"
#include "Support/Logging.h"
#include "llvm/ADT/StringSet.h"
#include "llvm/ADT/StringExtras.h"
#include "llvm/ADT/StringSet.h"
#include "llvm/Support/Allocator.h"
#include "llvm/Support/Process.h"
#include "llvm/Support/StringSaver.h"
#include "clang/Frontend/CompilerInstance.h"
#include "clang-tidy/ClangTidyOptions.h"
#include "clang-tidy/ClangTidyCheck.h"
#include "clang-tidy/ClangTidyModuleRegistry.h"
#include "clang-tidy/ClangTidyDiagnosticConsumer.h"
#include "clang-tidy/ClangTidyModuleRegistry.h"
#include "clang-tidy/ClangTidyOptions.h"
#define CLANG_TIDY_DISABLE_STATIC_ANALYZER_CHECKS
#include "clang-tidy/ClangTidyForceLinker.h"
@@ -201,7 +203,7 @@ public:
}
}
bool operator() (clang::diag::Group group_id) const {
bool operator()(clang::diag::Group group_id) const {
return exceptions.contains(static_cast<unsigned>(group_id)) ? !default_enable
: default_enable;
}

View File

@@ -5,16 +5,15 @@
#include "Compiler/Diagnostic.h"
#include "Compiler/Tidy.h"
#include "clang-tidy/ClangTidyCheck.h"
#include "clang-tidy/ClangTidyModuleRegistry.h"
#include "clang-tidy/ClangTidyOptions.h"
#include "clang-tidy/ClangTidyCheck.h"
namespace clice::tidy {
using namespace clang::tidy;
class ClangTidyChecker {
public:
/// The context of the clang-tidy checker.
ClangTidyContext context;

View File

@@ -1,16 +1,18 @@
#include "Compiler/Toolchain.h"
#include "Compiler/Command.h"
#include "Support/FileSystem.h"
#include "Support/Logging.h"
#include "llvm/ADT/ScopeExit.h"
#include "llvm/Support/CommandLine.h"
#include "llvm/Support/FileSystem.h"
#include "llvm/Support/Path.h"
#include "llvm/Support/Program.h"
#include "llvm/Support/FileSystem.h"
#include "clang/Driver/Driver.h"
#include "clang/Driver/Compilation.h"
#include "clang/Driver/Tool.h"
#include "llvm/Support/CommandLine.h"
#include "llvm/TargetParser/Host.h"
#include "clang/Driver/Compilation.h"
#include "clang/Driver/Driver.h"
#include "clang/Driver/Tool.h"
#ifndef _WIN32

View File

@@ -1,12 +1,14 @@
#include "AST/Utility.h"
#include "AST/SymbolKind.h"
#include "Compiler/Compilation.h"
#include "Feature/CodeCompletion.h"
#include "AST/SymbolKind.h"
#include "AST/Utility.h"
#include "Compiler/Compilation.h"
#include "Support/FuzzyMatcher.h"
#include "clang/Basic/CharInfo.h"
#include "clang/Sema/Sema.h"
#include "clang/Lex/Preprocessor.h"
#include "clang/Sema/CodeCompleteConsumer.h"
#include "clang/Sema/Sema.h"
namespace clice::feature {

View File

@@ -1,4 +1,5 @@
#include "Feature/Diagnostic.h"
#include "Compiler/CompilationUnit.h"
#include "Server/Convert.h"
#include "Support/Logging.h"

View File

@@ -1,7 +1,8 @@
#include "Compiler/CompilationUnit.h"
#include "Feature/DocumentLink.h"
#include "Support/Ranges.h"
#include "Compiler/CompilationUnit.h"
#include "Support/Compare.h"
#include "Support/Ranges.h"
namespace clice::feature {

View File

@@ -1,9 +1,10 @@
#include "Feature/DocumentSymbol.h"
#include "AST/FilterASTVisitor.h"
#include "AST/Utility.h"
#include "Compiler/Compilation.h"
#include "Feature/DocumentSymbol.h"
#include "Support/Ranges.h"
#include "Support/Compare.h"
#include "Support/Ranges.h"
namespace clice::feature {
@@ -46,7 +47,6 @@ std::string symbol_detail(clang::ASTContext& Ctx, const clang::NamedDecl& ND) {
/// Use DFS to traverse the AST and collect document symbols.
class DocumentSymbolCollector : public FilteredASTVisitor<DocumentSymbolCollector> {
public:
using Base = FilteredASTVisitor<DocumentSymbolCollector>;

View File

@@ -1,6 +1,7 @@
#include "Feature/FoldingRange.h"
#include "AST/FilterASTVisitor.h"
#include "Compiler/Compilation.h"
#include "Feature/FoldingRange.h"
#include "Support/Compare.h"
namespace clice::feature {
@@ -253,7 +254,6 @@ private:
/// Collect all condition macro's block as folding range.
void collect_condition_directive(const std::vector<Condition>& conds) {
// All condition directives have been stored in `conds` variable, ordered by presumed line
// number increasement, so use a stack to handle the branch structure.
llvm::SmallVector<const Condition*> stack = {};

View File

@@ -1,6 +1,8 @@
#include "Feature/Formatting.h"
#include "Support/Logging.h"
#include "Server/Convert.h"
#include "Support/Logging.h"
#include "clang/Format/Format.h"
namespace clice::feature {

View File

@@ -1,3 +1,5 @@
#include "Feature/Hover.h"
#include "AST/Selection.h"
#include "AST/Semantic.h"
#include "AST/Utility.h"
@@ -5,7 +7,6 @@
#include "Index/Shared.h"
#include "Support/Compare.h"
#include "Support/Ranges.h"
#include "Feature/Hover.h"
namespace clice::feature {

Some files were not shown because too many files have changed in this diff Show More