Skip to content

Commit

Permalink
Merge pull request duckdb#10579 from Tishj/unittest_require_flag
Browse files Browse the repository at this point in the history
[Tester] Add `--require <name>`
  • Loading branch information
Mytherin authored Feb 12, 2024
2 parents b985c34 + 66c20a5 commit 7de988e
Show file tree
Hide file tree
Showing 5 changed files with 188 additions and 103 deletions.
10 changes: 10 additions & 0 deletions test/helpers/test_helpers.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@
#include "duckdb/parser/parsed_data/copy_info.hpp"
#include "duckdb/main/client_context.hpp"
#include "duckdb/execution/operator/csv_scanner/scanner/string_value_scanner.hpp"
#include "duckdb/common/case_insensitive_map.hpp"

#include "pid.hpp"
#include "duckdb/function/table/read_csv.hpp"
Expand All @@ -23,6 +24,7 @@ namespace duckdb {
static string custom_test_directory;
static int debug_initialize_value = -1;
static bool single_threaded = false;
static case_insensitive_set_t required_requires;

bool NO_FAIL(QueryResult &result) {
if (result.HasError()) {
Expand Down Expand Up @@ -89,6 +91,14 @@ void SetSingleThreaded() {
single_threaded = true;
}

void AddRequire(string require) {
required_requires.insert(require);
}

bool IsRequired(string require) {
return required_requires.count(require);
}

string GetTestDirectory() {
if (custom_test_directory.empty()) {
return TESTING_DIRECTORY_NAME;
Expand Down
2 changes: 2 additions & 0 deletions test/include/test_helpers.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,8 @@ bool TestIsInternalError(unordered_set<string> &internal_error_messages, const s
void SetTestDirectory(string path);
void SetDebugInitialize(int value);
void SetSingleThreaded();
void AddRequire(string require);
bool IsRequired(string require);
string GetTestDirectory();
string GetCSVPath();
void WriteCSV(string path, const char *csv);
Expand Down
271 changes: 168 additions & 103 deletions test/sqlite/sqllogic_test_runner.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -206,6 +206,168 @@ bool SQLLogicTestRunner::ForEachTokenReplace(const string &parameter, vector<str
return collection;
}

RequireResult SQLLogicTestRunner::CheckRequire(SQLLogicParser &parser, const vector<string> &params) {
if (params.size() < 1) {
parser.Fail("require requires a single parameter");
}
// require command
string param = StringUtil::Lower(params[0]);
// os specific stuff
if (param == "notmingw") {
#ifdef __MINGW32__
return RequireResult::MISSING;
#else
return RequireResult::PRESENT;
#endif
}

if (param == "mingw") {
#ifndef __MINGW32__
return RequireResult::MISSING;
#else
return RequireResult::PRESENT;
#endif
}

if (param == "notwindows") {
#ifdef _WIN32
return RequireResult::MISSING;
#else
return RequireResult::PRESENT;
#endif
}

if (param == "windows") {
#ifndef _WIN32
return RequireResult::MISSING;
#else
return RequireResult::PRESENT;
#endif
}

if (param == "longdouble") {
#if LDBL_MANT_DIG < 54
return RequireResult::MISSING;
#else
return RequireResult::PRESENT;
#endif
}

if (param == "64bit") {
if (sizeof(void *) != 8) {
return RequireResult::MISSING;
}
return RequireResult::PRESENT;
}

if (param == "noforcestorage") {
if (TestForceStorage()) {
return RequireResult::MISSING;
}
return RequireResult::PRESENT;
}

if (param == "nothreadsan") {
#ifdef DUCKDB_THREAD_SANITIZER
return RequireResult::MISSING;
#else
return RequireResult::PRESENT;
#endif
}

if (param == "strinline") {
#ifdef DUCKDB_DEBUG_NO_INLINE
return RequireResult::MISSING;
#else
return RequireResult::PRESENT;
#endif
}

if (param == "vector_size") {
if (params.size() != 2) {
parser.Fail("require vector_size requires a parameter");
}
// require a specific vector size
auto required_vector_size = std::stoi(params[1]);
if (STANDARD_VECTOR_SIZE < required_vector_size) {
// vector size is too low for this test: skip it
return RequireResult::MISSING;
}
return RequireResult::PRESENT;
}

if (param == "exact_vector_size") {
if (params.size() != 2) {
parser.Fail("require exact_vector_size requires a parameter");
}
// require an exact vector size
auto required_vector_size = std::stoi(params[1]);
if (STANDARD_VECTOR_SIZE != required_vector_size) {
// vector size does not match the required vector size: skip it
return RequireResult::MISSING;
}
return RequireResult::PRESENT;
}

if (param == "block_size") {
if (params.size() != 2) {
parser.Fail("require block_size requires a parameter");
}
// require a specific block size
auto required_block_size = std::stoi(params[1]);
if (Storage::BLOCK_ALLOC_SIZE != required_block_size) {
// block size does not match the required block size: skip it
return RequireResult::MISSING;
}
return RequireResult::PRESENT;
}

if (param == "skip_reload") {
skip_reload = true;
return RequireResult::PRESENT;
}

if (param == "noalternativeverify") {
#ifdef DUCKDB_ALTERNATIVE_VERIFY
return RequireResult::MISSING;
#else
return RequireResult::PRESENT;
#endif
}

if (param == "no_extension_autoloading") {
if (config->options.autoload_known_extensions) {
// If autoloading is on, we skip this test
return RequireResult::MISSING;
}
return RequireResult::PRESENT;
}

bool excluded_from_autoloading = true;
for (const auto &ext : AUTOLOADABLE_EXTENSIONS) {
if (ext == param) {
excluded_from_autoloading = false;
break;
}
}

if (!config->options.autoload_known_extensions) {
auto result = ExtensionHelper::LoadExtension(*db, param);
if (result == ExtensionLoadResult::LOADED_EXTENSION) {
// add the extension to the list of loaded extensions
extensions.insert(param);
} else if (result == ExtensionLoadResult::EXTENSION_UNKNOWN) {
parser.Fail("unknown extension type: %s", params[0]);
} else if (result == ExtensionLoadResult::NOT_LOADED) {
// extension known but not build: skip this test
return RequireResult::MISSING;
}
} else if (excluded_from_autoloading) {
return RequireResult::MISSING;
}
return RequireResult::PRESENT;
}

void SQLLogicTestRunner::ExecuteFile(string script) {
SQLLogicParser parser;
idx_t skip_level = 0;
Expand Down Expand Up @@ -473,111 +635,14 @@ void SQLLogicTestRunner::ExecuteFile(string script) {
} else if (token.type == SQLLogicTokenType::SQLLOGIC_ENDLOOP) {
EndLoop();
} else if (token.type == SQLLogicTokenType::SQLLOGIC_REQUIRE) {
if (token.parameters.size() < 1) {
parser.Fail("require requires a single parameter");
}
// require command
string param = StringUtil::Lower(token.parameters[0]);
// os specific stuff
if (param == "notmingw") {
#ifdef __MINGW32__
return;
#endif
} else if (param == "mingw") {
#ifndef __MINGW32__
return;
#endif
} else if (param == "notwindows") {
#ifdef _WIN32
return;
#endif
} else if (param == "windows") {
#ifndef _WIN32
return;
#endif
} else if (param == "longdouble") {
#if LDBL_MANT_DIG < 54
return;
#endif
} else if (param == "64bit") {
if (sizeof(void *) != 8) {
return;
auto require_result = CheckRequire(parser, token.parameters);
if (require_result == RequireResult::MISSING) {
auto &param = token.parameters[0];
if (IsRequired(param)) {
// This extension / setting was explicitly required
parser.Fail(StringUtil::Format("require %s: FAILED", param));
}
} else if (param == "noforcestorage") {
if (TestForceStorage()) {
return;
}
} else if (param == "nothreadsan") {
#ifdef DUCKDB_THREAD_SANITIZER
return;
#endif
} else if (param == "strinline") {
#ifdef DUCKDB_DEBUG_NO_INLINE
return;
#endif
} else if (param == "vector_size") {
if (token.parameters.size() != 2) {
parser.Fail("require vector_size requires a parameter");
}
// require a specific vector size
auto required_vector_size = std::stoi(token.parameters[1]);
if (STANDARD_VECTOR_SIZE < required_vector_size) {
// vector size is too low for this test: skip it
return;
}
} else if (param == "exact_vector_size") {
if (token.parameters.size() != 2) {
parser.Fail("require exact_vector_size requires a parameter");
}
// require an exact vector size
auto required_vector_size = std::stoi(token.parameters[1]);
if (STANDARD_VECTOR_SIZE != required_vector_size) {
// vector size does not match the required vector size: skip it
return;
}
} else if (param == "block_size") {
if (token.parameters.size() != 2) {
parser.Fail("require block_size requires a parameter");
}
// require a specific block size
auto required_block_size = std::stoi(token.parameters[1]);
if (Storage::BLOCK_ALLOC_SIZE != required_block_size) {
// block size does not match the required block size: skip it
return;
}
} else if (param == "skip_reload") {
skip_reload = true;
} else if (param == "noalternativeverify") {
#ifdef DUCKDB_ALTERNATIVE_VERIFY
return;
#endif
} else if (param == "no_extension_autoloading") {
if (config->options.autoload_known_extensions) {
return;
}
} else {
bool excluded_from_autoloading = true;
for (const auto &ext : AUTOLOADABLE_EXTENSIONS) {
if (ext == param) {
excluded_from_autoloading = false;
break;
}
}

if (!config->options.autoload_known_extensions) {
auto result = ExtensionHelper::LoadExtension(*db, param);
if (result == ExtensionLoadResult::LOADED_EXTENSION) {
// add the extension to the list of loaded extensions
extensions.insert(param);
} else if (result == ExtensionLoadResult::EXTENSION_UNKNOWN) {
parser.Fail("unknown extension type: %s", token.parameters[0]);
} else if (result == ExtensionLoadResult::NOT_LOADED) {
// extension known but not build: skip this test
return;
}
} else if (excluded_from_autoloading) {
return;
}
}
} else if (token.type == SQLLogicTokenType::SQLLOGIC_REQUIRE_ENV) {
if (InLoop()) {
Expand Down
6 changes: 6 additions & 0 deletions test/sqlite/sqllogic_test_runner.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,9 @@ namespace duckdb {

class Command;
class LoopCommand;
class SQLLogicParser;

enum class RequireResult { PRESENT, MISSING };

class SQLLogicTestRunner {
public:
Expand Down Expand Up @@ -68,6 +71,9 @@ class SQLLogicTestRunner {
static string ReplaceLoopIterator(string text, string loop_iterator_name, string replacement);
static string LoopReplacement(string text, const vector<LoopDefinition> &loops);
static bool ForEachTokenReplace(const string &parameter, vector<string> &result);

private:
RequireResult CheckRequire(SQLLogicParser &parser, const vector<string> &params);
};

} // namespace duckdb
2 changes: 2 additions & 0 deletions test/unittest.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -52,6 +52,8 @@ int main(int argc, char *argv[]) {
return 1;
}
SetTestDirectory(test_dir);
} else if (string(argv[i]) == "--require") {
AddRequire(string(argv[++i]));
} else if (string(argv[i]) == "--zero-initialize") {
SetDebugInitialize(0);
} else if (string(argv[i]) == "--one-initialize") {
Expand Down

0 comments on commit 7de988e

Please sign in to comment.