diff options
Diffstat (limited to 'src/unittest')
-rw-r--r-- | src/unittest/CMakeLists.txt | 6 | ||||
-rw-r--r-- | src/unittest/test_filepath.cpp | 3 | ||||
-rw-r--r-- | src/unittest/test_keycode.cpp | 129 | ||||
-rw-r--r-- | src/unittest/test_map_settings_manager.cpp | 261 | ||||
-rw-r--r-- | src/unittest/test_player.cpp | 88 | ||||
-rw-r--r-- | src/unittest/test_settings.cpp | 7 | ||||
-rw-r--r-- | src/unittest/test_threading.cpp | 3 |
7 files changed, 495 insertions, 2 deletions
diff --git a/src/unittest/CMakeLists.txt b/src/unittest/CMakeLists.txt index a07ed8ba5..7ad38099c 100644 --- a/src/unittest/CMakeLists.txt +++ b/src/unittest/CMakeLists.txt @@ -6,11 +6,13 @@ set (UNITTEST_SRCS ${CMAKE_CURRENT_SOURCE_DIR}/test_connection.cpp ${CMAKE_CURRENT_SOURCE_DIR}/test_filepath.cpp ${CMAKE_CURRENT_SOURCE_DIR}/test_inventory.cpp + ${CMAKE_CURRENT_SOURCE_DIR}/test_map_settings_manager.cpp ${CMAKE_CURRENT_SOURCE_DIR}/test_mapnode.cpp ${CMAKE_CURRENT_SOURCE_DIR}/test_nodedef.cpp ${CMAKE_CURRENT_SOURCE_DIR}/test_noderesolver.cpp ${CMAKE_CURRENT_SOURCE_DIR}/test_noise.cpp ${CMAKE_CURRENT_SOURCE_DIR}/test_objdef.cpp + ${CMAKE_CURRENT_SOURCE_DIR}/test_player.cpp ${CMAKE_CURRENT_SOURCE_DIR}/test_profiler.cpp ${CMAKE_CURRENT_SOURCE_DIR}/test_random.cpp ${CMAKE_CURRENT_SOURCE_DIR}/test_schematic.cpp @@ -22,3 +24,7 @@ set (UNITTEST_SRCS ${CMAKE_CURRENT_SOURCE_DIR}/test_voxelalgorithms.cpp ${CMAKE_CURRENT_SOURCE_DIR}/test_voxelmanipulator.cpp PARENT_SCOPE) + +set (UNITTEST_CLIENT_SRCS + ${CMAKE_CURRENT_SOURCE_DIR}/test_keycode.cpp + PARENT_SCOPE) diff --git a/src/unittest/test_filepath.cpp b/src/unittest/test_filepath.cpp index 6ea7ac076..ac2d69b5a 100644 --- a/src/unittest/test_filepath.cpp +++ b/src/unittest/test_filepath.cpp @@ -252,6 +252,9 @@ void TestFilePath::testRemoveRelativePathComponent() path = p("."); result = fs::RemoveRelativePathComponents(path); UASSERT(result == ""); + path = p("../a"); + result = fs::RemoveRelativePathComponents(path); + UASSERT(result == ""); path = p("./subdir/../.."); result = fs::RemoveRelativePathComponents(path); UASSERT(result == ""); diff --git a/src/unittest/test_keycode.cpp b/src/unittest/test_keycode.cpp new file mode 100644 index 000000000..dd3d75a5b --- /dev/null +++ b/src/unittest/test_keycode.cpp @@ -0,0 +1,129 @@ +/* +Minetest +Copyright (C) 2016 sfan5 <sfan5@live.de> + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU Lesser General Public License as published by +the Free Software Foundation; either version 2.1 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU Lesser General Public License for more details. + +You should have received a copy of the GNU Lesser General Public License along +with this program; if not, write to the Free Software Foundation, Inc., +51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. +*/ + +#include "test.h" + +#include <string> +#include "exceptions.h" +#include "keycode.h" + +class TestKeycode : public TestBase { +public: + TestKeycode() { TestManager::registerTestModule(this); } + const char *getName() { return "TestKeycode"; } + + void runTests(IGameDef *gamedef); + + void testCreateFromString(); + void testCreateFromSKeyInput(); + void testCompare(); +}; + +static TestKeycode g_test_instance; + +void TestKeycode::runTests(IGameDef *gamedef) +{ + TEST(testCreateFromString); + TEST(testCreateFromSKeyInput); + TEST(testCompare); +} + +//////////////////////////////////////////////////////////////////////////////// + +#define UASSERTEQ_STR(one, two) UASSERT(strcmp(one, two) == 0) + +void TestKeycode::testCreateFromString() +{ + KeyPress k; + + // Character key, from char + k = KeyPress("R"); + UASSERTEQ_STR(k.sym(), "KEY_KEY_R"); + UASSERTCMP(int, >, strlen(k.name()), 0); // should have human description + + // Character key, from identifier + k = KeyPress("KEY_KEY_B"); + UASSERTEQ_STR(k.sym(), "KEY_KEY_B"); + UASSERTCMP(int, >, strlen(k.name()), 0); + + // Non-Character key, from identifier + k = KeyPress("KEY_UP"); + UASSERTEQ_STR(k.sym(), "KEY_UP"); + UASSERTCMP(int, >, strlen(k.name()), 0); + + k = KeyPress("KEY_F6"); + UASSERTEQ_STR(k.sym(), "KEY_F6"); + UASSERTCMP(int, >, strlen(k.name()), 0); + + // Irrlicht-unknown key, from char + k = KeyPress("/"); + UASSERTEQ_STR(k.sym(), "/"); + UASSERTCMP(int, >, strlen(k.name()), 0); +} + +void TestKeycode::testCreateFromSKeyInput() +{ + KeyPress k; + irr::SEvent::SKeyInput in; + + // Character key + in.Key = irr::KEY_KEY_3; + in.Char = L'3'; + k = KeyPress(in); + UASSERTEQ_STR(k.sym(), "KEY_KEY_3"); + + // Non-Character key + in.Key = irr::KEY_RSHIFT; + in.Char = L'\0'; + k = KeyPress(in); + UASSERTEQ_STR(k.sym(), "KEY_RSHIFT"); + + // Irrlicht-unknown key + in.Key = irr::KEY_KEY_CODES_COUNT; + in.Char = L'?'; + k = KeyPress(in); + UASSERTEQ_STR(k.sym(), "?"); + + // prefer_character mode + in.Key = irr::KEY_COMMA; + in.Char = L'G'; + k = KeyPress(in, true); + UASSERTEQ_STR(k.sym(), "KEY_KEY_G"); +} + +void TestKeycode::testCompare() +{ + // Basic comparison + UASSERT(KeyPress("5") == KeyPress("KEY_KEY_5")); + UASSERT(!(KeyPress("5") == KeyPress("KEY_NUMPAD_5"))); + + // Matching char suffices + // note: This is a real-world example, Irrlicht maps XK_equal to irr::KEY_PLUS on Linux + irr::SEvent::SKeyInput in; + in.Key = irr::KEY_PLUS; + in.Char = L'='; + UASSERT(KeyPress("=") == KeyPress(in)); + + // Matching keycode suffices + irr::SEvent::SKeyInput in2; + in.Key = in2.Key = irr::KEY_OEM_CLEAR; + in.Char = L'\0'; + in2.Char = L';'; + UASSERT(KeyPress(in) == KeyPress(in2)); +} diff --git a/src/unittest/test_map_settings_manager.cpp b/src/unittest/test_map_settings_manager.cpp new file mode 100644 index 000000000..4f5ac80f2 --- /dev/null +++ b/src/unittest/test_map_settings_manager.cpp @@ -0,0 +1,261 @@ + /* +Minetest +Copyright (C) 2010-2014 kwolekr, Ryan Kwolek <kwolekr@minetest.net> + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU Lesser General Public License as published by +the Free Software Foundation; either version 2.1 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU Lesser General Public License for more details. + +You should have received a copy of the GNU Lesser General Public License along +with this program; if not, write to the Free Software Foundation, Inc., +51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. +*/ + +#include "test.h" + +#include "noise.h" +#include "settings.h" +#include "mapgen_v5.h" +#include "util/sha1.h" +#include "map_settings_manager.h" + +class TestMapSettingsManager : public TestBase { +public: + TestMapSettingsManager() { TestManager::registerTestModule(this); } + const char *getName() { return "TestMapSettingsManager"; } + + void makeUserConfig(Settings *conf); + std::string makeMetaFile(bool make_corrupt); + + void runTests(IGameDef *gamedef); + + void testMapSettingsManager(); + void testMapMetaSaveLoad(); + void testMapMetaFailures(); +}; + +static TestMapSettingsManager g_test_instance; + +void TestMapSettingsManager::runTests(IGameDef *gamedef) +{ + TEST(testMapSettingsManager); + TEST(testMapMetaSaveLoad); + TEST(testMapMetaFailures); +} + +//////////////////////////////////////////////////////////////////////////////// + + +void check_noise_params(const NoiseParams *np1, const NoiseParams *np2) +{ + UASSERTEQ(float, np1->offset, np2->offset); + UASSERTEQ(float, np1->scale, np2->scale); + UASSERT(np1->spread == np2->spread); + UASSERTEQ(s32, np1->seed, np2->seed); + UASSERTEQ(u16, np1->octaves, np2->octaves); + UASSERTEQ(float, np1->persist, np2->persist); + UASSERTEQ(float, np1->lacunarity, np2->lacunarity); + UASSERTEQ(u32, np1->flags, np2->flags); +} + + +std::string read_file_to_string(const std::string &filepath) +{ + std::string buf; + FILE *f = fopen(filepath.c_str(), "rb"); + if (!f) + return ""; + + fseek(f, 0, SEEK_END); + + long filesize = ftell(f); + if (filesize == -1) { + fclose(f); + return ""; + } + rewind(f); + + buf.resize(filesize); + + UASSERTEQ(size_t, fread(&buf[0], 1, filesize, f), 1); + + fclose(f); + return buf; +} + + +void TestMapSettingsManager::makeUserConfig(Settings *conf) +{ + conf->set("mg_name", "v7"); + conf->set("seed", "5678"); + conf->set("water_level", "20"); + conf->set("mgv5_np_factor", "0, 12, (500, 250, 500), 920382, 5, 0.45, 3.0"); + conf->set("mgv5_np_height", "0, 15, (500, 250, 500), 841746, 5, 0.5, 3.0"); + conf->set("mgv5_np_filler_depth", "20, 1, (150, 150, 150), 261, 4, 0.7, 1.0"); + conf->set("mgv5_np_ground", "-43, 40, (80, 80, 80), 983240, 4, 0.55, 2.0"); +} + + +std::string TestMapSettingsManager::makeMetaFile(bool make_corrupt) +{ + std::string metafile = getTestTempFile(); + + const char *metafile_contents = + "mg_name = v5\n" + "seed = 1234\n" + "mg_flags = light\n" + "mgv5_np_filler_depth = 20, 1, (150, 150, 150), 261, 4, 0.7, 1.0\n" + "mgv5_np_height = 20, 10, (250, 250, 250), 84174, 4, 0.5, 1.0\n"; + + FILE *f = fopen(metafile.c_str(), "wb"); + UASSERT(f != NULL); + + fputs(metafile_contents, f); + if (!make_corrupt) + fputs("[end_of_params]\n", f); + + fclose(f); + + return metafile; +} + + +void TestMapSettingsManager::testMapSettingsManager() +{ + Settings user_settings; + makeUserConfig(&user_settings); + + std::string test_mapmeta_path = makeMetaFile(false); + + MapSettingsManager mgr(&user_settings, test_mapmeta_path); + std::string value; + + UASSERT(mgr.getMapSetting("mg_name", &value)); + UASSERT(value == "v7"); + + // Pretend we're initializing the ServerMap + UASSERT(mgr.loadMapMeta()); + + // Pretend some scripts are requesting mapgen params + UASSERT(mgr.getMapSetting("mg_name", &value)); + UASSERT(value == "v5"); + UASSERT(mgr.getMapSetting("seed", &value)); + UASSERT(value == "1234"); + UASSERT(mgr.getMapSetting("water_level", &value)); + UASSERT(value == "20"); + + // Pretend we have some mapgen settings configured from the scripting + UASSERT(mgr.setMapSetting("water_level", "15")); + UASSERT(mgr.setMapSetting("seed", "02468")); + UASSERT(mgr.setMapSetting("mg_flags", "nolight", true)); + + NoiseParams script_np_filler_depth(0, 100, v3f(200, 100, 200), 261, 4, 0.7, 2.0); + NoiseParams script_np_factor(0, 100, v3f(50, 50, 50), 920381, 3, 0.45, 2.0); + NoiseParams script_np_height(0, 100, v3f(450, 450, 450), 84174, 4, 0.5, 2.0); + NoiseParams meta_np_height(20, 10, v3f(250, 250, 250), 84174, 4, 0.5, 1.0); + NoiseParams user_np_ground(-43, 40, v3f(80, 80, 80), 983240, 4, 0.55, 2.0, NOISE_FLAG_EASED); + + mgr.setMapSettingNoiseParams("mgv5_np_filler_depth", &script_np_filler_depth, true); + mgr.setMapSettingNoiseParams("mgv5_np_height", &script_np_height); + mgr.setMapSettingNoiseParams("mgv5_np_factor", &script_np_factor); + + // Now make our Params and see if the values are correctly sourced + MapgenParams *params = mgr.makeMapgenParams(); + UASSERT(params->mgtype == MAPGEN_V5); + UASSERT(params->chunksize == 5); + UASSERT(params->water_level == 15); + UASSERT(params->seed == 1234); + UASSERT((params->flags & MG_LIGHT) == 0); + + MapgenV5Params *v5params = (MapgenV5Params *)params; + + check_noise_params(&v5params->np_filler_depth, &script_np_filler_depth); + check_noise_params(&v5params->np_factor, &script_np_factor); + check_noise_params(&v5params->np_height, &meta_np_height); + check_noise_params(&v5params->np_ground, &user_np_ground); + + UASSERT(mgr.setMapSetting("foobar", "25") == false); + + // Pretend the ServerMap is shutting down + UASSERT(mgr.saveMapMeta()); + + // Make sure our interface expectations are met + UASSERT(mgr.mapgen_params == params); + UASSERT(mgr.makeMapgenParams() == params); + +#if 0 + // TODO(paramat or hmmmm): change this to compare the result against a static file + + // Load the resulting map_meta.txt and make sure it contains what we expect + unsigned char expected_contents_hash[20] = { + 0x48, 0x3f, 0x88, 0x5a, 0xc0, 0x7a, 0x14, 0x48, 0xa4, 0x71, + 0x78, 0x56, 0x95, 0x2d, 0xdc, 0x6a, 0xf7, 0x61, 0x36, 0x5f + }; + + SHA1 ctx; + std::string metafile_contents = read_file_to_string(test_mapmeta_path); + ctx.addBytes(&metafile_contents[0], metafile_contents.size()); + unsigned char *sha1_result = ctx.getDigest(); + int resultdiff = memcmp(sha1_result, expected_contents_hash, 20); + free(sha1_result); + + UASSERT(!resultdiff); +#endif +} + + +void TestMapSettingsManager::testMapMetaSaveLoad() +{ + Settings conf; + std::string path = getTestTempDirectory() + + DIR_DELIM + "foobar" + DIR_DELIM + "map_meta.txt"; + + // Create a set of mapgen params and save them to map meta + conf.set("seed", "12345"); + conf.set("water_level", "5"); + MapSettingsManager mgr1(&conf, path); + MapgenParams *params1 = mgr1.makeMapgenParams(); + UASSERT(params1); + UASSERT(mgr1.saveMapMeta()); + + // Now try loading the map meta to mapgen params + conf.set("seed", "67890"); + conf.set("water_level", "32"); + MapSettingsManager mgr2(&conf, path); + UASSERT(mgr2.loadMapMeta()); + MapgenParams *params2 = mgr2.makeMapgenParams(); + UASSERT(params2); + + // Check that both results are correct + UASSERTEQ(u64, params1->seed, 12345); + UASSERTEQ(s16, params1->water_level, 5); + UASSERTEQ(u64, params2->seed, 12345); + UASSERTEQ(s16, params2->water_level, 5); +} + + +void TestMapSettingsManager::testMapMetaFailures() +{ + std::string test_mapmeta_path; + Settings conf; + + // Check to see if it'll fail on a non-existent map meta file + test_mapmeta_path = "woobawooba/fgdfg/map_meta.txt"; + UASSERT(!fs::PathExists(test_mapmeta_path)); + + MapSettingsManager mgr1(&conf, test_mapmeta_path); + UASSERT(!mgr1.loadMapMeta()); + + // Check to see if it'll fail on a corrupt map meta file + test_mapmeta_path = makeMetaFile(true); + UASSERT(fs::PathExists(test_mapmeta_path)); + + MapSettingsManager mgr2(&conf, test_mapmeta_path); + UASSERT(!mgr2.loadMapMeta()); +} diff --git a/src/unittest/test_player.cpp b/src/unittest/test_player.cpp new file mode 100644 index 000000000..85fbc8b2d --- /dev/null +++ b/src/unittest/test_player.cpp @@ -0,0 +1,88 @@ +/* +Minetest +Copyright (C) 2010-2016 nerzhul, Loic Blot <loic.blot@unix-experience.fr> + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU Lesser General Public License as published by +the Free Software Foundation; either version 2.1 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU Lesser General Public License for more details. + +You should have received a copy of the GNU Lesser General Public License along +with this program; if not, write to the Free Software Foundation, Inc., +51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. +*/ + +#include "test.h" + +#include "exceptions.h" +#include "remoteplayer.h" +#include "content_sao.h" +#include "server.h" + +class TestPlayer : public TestBase { +public: + TestPlayer() { TestManager::registerTestModule(this); } + const char *getName() { return "TestPlayer"; } + + void runTests(IGameDef *gamedef); + + void testSave(IGameDef *gamedef); + void testLoad(IGameDef *gamedef); +}; + +static TestPlayer g_test_instance; + +void TestPlayer::runTests(IGameDef *gamedef) +{ + TEST(testSave, gamedef); + TEST(testLoad, gamedef); +} + +void TestPlayer::testSave(IGameDef *gamedef) +{ + RemotePlayer rplayer("testplayer_save", gamedef->idef()); + PlayerSAO sao(NULL, 1, false); + sao.initialize(&rplayer, std::set<std::string>()); + rplayer.setPlayerSAO(&sao); + sao.setBreath(10); + sao.setHPRaw(8); + sao.setYaw(0.1f); + sao.setPitch(0.6f); + sao.setBasePosition(v3f(450.2f, -15.7f, 68.1f)); + rplayer.save(".", gamedef); + UASSERT(fs::PathExists("testplayer_save")); +} + +void TestPlayer::testLoad(IGameDef *gamedef) +{ + RemotePlayer rplayer("testplayer_load", gamedef->idef()); + PlayerSAO sao(NULL, 1, false); + sao.initialize(&rplayer, std::set<std::string>()); + rplayer.setPlayerSAO(&sao); + sao.setBreath(10); + sao.setHPRaw(8); + sao.setYaw(0.1f); + sao.setPitch(0.6f); + sao.setBasePosition(v3f(450.2f, -15.7f, 68.1f)); + rplayer.save(".", gamedef); + UASSERT(fs::PathExists("testplayer_load")); + + RemotePlayer rplayer_load("testplayer_load", gamedef->idef()); + PlayerSAO sao_load(NULL, 2, false); + std::ifstream is("testplayer_load", std::ios_base::binary); + UASSERT(is.good()); + rplayer_load.deSerialize(is, "testplayer_load", &sao_load); + is.close(); + + UASSERT(strcmp(rplayer_load.getName(), "testplayer_load") == 0); + UASSERT(sao_load.getBreath() == 10); + UASSERT(sao_load.getHP() == 8); + UASSERT(sao_load.getYaw() == 0.1f); + UASSERT(sao_load.getPitch() == 0.6f); + UASSERT(sao_load.getBasePosition() == v3f(450.2f, -15.7f, 68.1f)); +} diff --git a/src/unittest/test_settings.cpp b/src/unittest/test_settings.cpp index a82d734f0..733c7e92a 100644 --- a/src/unittest/test_settings.cpp +++ b/src/unittest/test_settings.cpp @@ -32,7 +32,7 @@ public: void testAllSettings(); static const char *config_text_before; - static const char *config_text_after; + static const std::string config_text_after; }; static TestSettings g_test_instance; @@ -69,7 +69,7 @@ const char *TestSettings::config_text_before = "np_terrain = 5, 40, (250, 250, 250), 12341, 5, 0.7, 2.4\n" "zoop = true"; -const char *TestSettings::config_text_after = +const std::string TestSettings::config_text_after = "leet = 1337\n" "leetleet = 13371337\n" "leetleet_neg = -13371337\n" @@ -197,7 +197,10 @@ void TestSettings::testAllSettings() UASSERT(s.updateConfigObject(is, os, "", 0) == true); //printf(">>>> expected config:\n%s\n", TEST_CONFIG_TEXT_AFTER); //printf(">>>> actual config:\n%s\n", os.str().c_str()); +#if __cplusplus < 201103L + // This test only works in older C++ versions than C++11 because we use unordered_map UASSERT(os.str() == config_text_after); +#endif } catch (SettingNotFoundException &e) { UASSERT(!"Setting not found!"); } diff --git a/src/unittest/test_threading.cpp b/src/unittest/test_threading.cpp index f0df85b2d..cdbf9674e 100644 --- a/src/unittest/test_threading.cpp +++ b/src/unittest/test_threading.cpp @@ -39,7 +39,9 @@ static TestThreading g_test_instance; void TestThreading::runTests(IGameDef *gamedef) { +#if !(defined(__MACH__) && defined(__APPLE__)) TEST(testStartStopWait); +#endif TEST(testThreadKill); TEST(testAtomicSemaphoreThread); } @@ -161,6 +163,7 @@ private: void TestThreading::testAtomicSemaphoreThread() { Atomic<u32> val; + val = 0; Semaphore trigger; static const u8 num_threads = 4; |