1
0
mirror of https://github.com/OpenRCT2/OpenRCT2 synced 2025-12-23 07:43:01 +01:00

Use C++ filesystem for more file/path functions

This commit is contained in:
Gymnasiast
2022-01-08 18:38:09 +01:00
parent 10301507a9
commit 6bcf848b2f
26 changed files with 62 additions and 176 deletions

View File

@@ -12,6 +12,7 @@
#include <openrct2-ui/windows/Window.h>
#include <openrct2/Context.h>
#include <openrct2/audio/audio.h>
#include <openrct2/core/File.h>
#include <openrct2/localisation/Formatter.h>
#include <openrct2/localisation/Localisation.h>
#include <openrct2/object/ObjectManager.h>
@@ -442,7 +443,7 @@ static void WindowInstallTrackDesign(rct_window* w)
safe_strcat_path(destPath, _trackName.c_str(), sizeof(destPath));
path_append_extension(destPath, ".td6", sizeof(destPath));
if (Platform::FileExists(destPath))
if (File::Exists(destPath))
{
log_info("%s already exists, prompting user for a different track design name", destPath);
context_show_error(STR_UNABLE_TO_INSTALL_THIS_TRACK_DESIGN, STR_NONE, {});

View File

@@ -226,7 +226,7 @@ static const char* GetFilterPatternByType(const int32_t type, const bool isSave)
static int32_t WindowLoadsaveGetDir(const int32_t type, char* path, size_t pathSize)
{
const char* last_save = GetLastDirectoryByType(type);
if (last_save != nullptr && platform_directory_exists(last_save))
if (last_save != nullptr && Path::DirectoryExists(last_save))
safe_strcpy(path, last_save, pathSize);
else
GetInitialDirectoryByType(type, path, pathSize);

View File

@@ -25,6 +25,7 @@
#include <openrct2/audio/AudioMixer.h>
#include <openrct2/audio/audio.h>
#include <openrct2/config/Config.h>
#include <openrct2/core/File.h>
#include <openrct2/core/String.hpp>
#include <openrct2/drawing/IDrawingEngine.h>
#include <openrct2/localisation/Currency.h>
@@ -1646,7 +1647,7 @@ private:
this->Invalidate();
break;
case WIDX_TITLE_MUSIC_DROPDOWN:
if ((dropdownIndex == 1 || dropdownIndex == 3) && !Platform::FileExists(context_get_path_legacy(PATH_ID_CSS50)))
if ((dropdownIndex == 1 || dropdownIndex == 3) && !File::Exists(context_get_path_legacy(PATH_ID_CSS50)))
{
context_show_error(STR_OPTIONS_MUSIC_ERR_CSS50_NOT_FOUND, STR_OPTIONS_MUSIC_ERR_CSS50_NOT_FOUND_HINT, {});
}

View File

@@ -1208,7 +1208,7 @@ namespace OpenRCT2
auto dstDirectory = Path::GetDirectory(dst);
// Create the directory if necessary
if (!platform_directory_exists(dstDirectory.c_str()))
if (!Path::DirectoryExists(dstDirectory.c_str()))
{
Console::WriteLine("Creating directory '%s'", dstDirectory.c_str());
if (!platform_ensure_directory_exists(dstDirectory.c_str()))

View File

@@ -698,7 +698,7 @@ void game_autosave()
safe_strcat(backupPath, fileExtension, sizeof(backupPath));
safe_strcat(backupPath, ".bak", sizeof(backupPath));
if (Platform::FileExists(path))
if (File::Exists(path))
{
File::Copy(path, backupPath, true);
}

View File

@@ -17,6 +17,7 @@
# include "../OpenRCT2.h"
# include "../audio/audio.h"
# include "../core/Console.hpp"
# include "../core/File.h"
# include "../core/Imaging.h"
# include "../drawing/Drawing.h"
# include "../interface/Viewport.h"
@@ -183,7 +184,7 @@ static int cmdline_for_bench_sprite_sort(int argc, const char** argv)
// Extract file names from argument list. If there is no such file, consider it benchmark option.
for (int i = 0; i < argc; i++)
{
if (Platform::FileExists(argv[i]))
if (File::Exists(argv[i]))
{
// Register benchmark for sv6 if valid
std::vector<RecordedPaintSession> sessions = extract_paint_session(argv[i]);

View File

@@ -14,6 +14,7 @@
# include "../Context.h"
# include "../GameState.h"
# include "../OpenRCT2.h"
# include "../core/File.h"
# include "../platform/Platform2.h"
# include "../platform/platform.h"
@@ -102,7 +103,7 @@ static int CmdlineForBenchSpriteSort(int argc, const char* const* argv)
// Extract file names from argument list. If there is no such file, consider it benchmark option.
for (int i = 0; i < argc; i++)
{
if (Platform::FileExists(argv[i]))
if (File::Exists(argv[i]))
{
// Register benchmark for sv6 if valid
benchmark::RegisterBenchmark(argv[i], BM_update, argv[i]);

View File

@@ -13,6 +13,7 @@
#include "../Version.h"
#include "../config/Config.h"
#include "../core/Console.hpp"
#include "../core/File.h"
#include "../core/Guard.hpp"
#include "../core/Memory.hpp"
#include "../core/Path.hpp"
@@ -354,7 +355,7 @@ static exitcode_t HandleCommandSetRCT2(CommandLineArgEnumerator* enumerator)
// Check if path exists
Console::WriteLine("Checking path...");
if (!platform_directory_exists(path))
if (!Path::DirectoryExists(path))
{
Console::Error::WriteLine("The path '%s' does not exist", path);
return EXITCODE_FAIL;
@@ -367,7 +368,7 @@ static exitcode_t HandleCommandSetRCT2(CommandLineArgEnumerator* enumerator)
String::Set(pathG1Check, sizeof(pathG1Check), path);
Path::Append(pathG1Check, sizeof(pathG1Check), "Data");
Path::Append(pathG1Check, sizeof(pathG1Check), "g1.dat");
if (!Platform::FileExists(pathG1Check))
if (!File::Exists(pathG1Check))
{
Console::Error::WriteLine("RCT2 path not valid.");
Console::Error::WriteLine("Unable to find %s.", pathG1Check);

View File

@@ -25,22 +25,38 @@ namespace File
{
bool Exists(std::string_view path)
{
return Platform::FileExists(path);
fs::path file = u8path(path);
log_verbose("Checking if file exists: %s", std::string(path).c_str());
return fs::exists(file);
}
bool Copy(std::string_view srcPath, std::string_view dstPath, bool overwrite)
{
return Platform::CopyFile(srcPath, dstPath, overwrite);
if (!overwrite && Exists(dstPath))
{
log_warning("File::Copy(): Not overwriting %s, because overwrite flag == false", std::string(dstPath).c_str());
return false;
}
return fs::copy_file(u8path(srcPath), u8path(dstPath));
}
bool Delete(std::string_view path)
{
return Platform::DeleteFile(path);
return fs::remove(u8path(path));
}
bool Move(std::string_view srcPath, std::string_view dstPath)
{
return Platform::MoveFile(srcPath, dstPath);
try
{
fs::rename(u8path(srcPath), u8path(dstPath));
return true;
}
catch (const fs::filesystem_error&)
{
return false;
}
}
std::vector<uint8_t> ReadAllBytes(std::string_view path)

View File

@@ -56,26 +56,7 @@ namespace Path
std::string GetDirectory(std::string_view path)
{
size_t maxSize = String::SizeOf(std::string(path).c_str()) + 1;
utf8* buffer = Memory::Allocate<utf8>(maxSize);
GetDirectory(buffer, maxSize, std::string(path).c_str());
std::string result(buffer);
Memory::Free(buffer);
return result;
}
utf8* GetDirectory(utf8* buffer, size_t bufferSize, const utf8* path)
{
auto lastPathSepIndex = std::max(String::LastIndexOf(path, *PATH_SEPARATOR), String::LastIndexOf(path, '/'));
if (lastPathSepIndex < 0)
{
return String::Set(buffer, bufferSize, String::Empty);
}
size_t copyLength = std::min(lastPathSepIndex, static_cast<ptrdiff_t>(bufferSize - 1));
std::copy_n(path, copyLength, buffer);
buffer[copyLength] = '\0';
return buffer;
return u8path(path).parent_path().string();
}
void CreateDirectory(std::string_view path)
@@ -85,7 +66,7 @@ namespace Path
bool DirectoryExists(std::string_view path)
{
return platform_directory_exists(std::string(path).c_str());
return fs::is_directory(u8path(path));
}
std::string GetFileName(std::string_view path)

View File

@@ -24,7 +24,6 @@ namespace Path
}
std::string GetDirectory(std::string_view path);
utf8* GetDirectory(utf8* buffer, size_t bufferSize, const utf8* path);
void CreateDirectory(std::string_view path);
bool DirectoryExists(std::string_view path);
std::string GetFileName(std::string_view origPath);

View File

@@ -17,6 +17,7 @@
#include "../actions/SetCheatAction.h"
#include "../audio/audio.h"
#include "../core/Console.hpp"
#include "../core/File.h"
#include "../core/Imaging.h"
#include "../drawing/Drawing.h"
#include "../drawing/X8DrawingEngine.h"
@@ -147,7 +148,7 @@ static std::optional<std::string> screenshot_get_next_path()
for (int tries = 0; tries < 100; tries++)
{
auto path = pathComposer(tries);
if (!Platform::FileExists(path))
if (!File::Exists(path))
{
return path;
}

View File

@@ -17,6 +17,7 @@
#include "../actions/LoadOrQuitAction.h"
#include "../actions/NetworkModifyGroupAction.h"
#include "../actions/PeepPickupAction.h"
#include "../core/File.h"
#include "../core/Guard.hpp"
#include "../core/Json.hpp"
#include "../entity/EntityList.h"
@@ -277,7 +278,7 @@ bool NetworkBase::BeginClient(const std::string& host, uint16_t port)
utf8 keyPath[MAX_PATH];
network_get_private_key_path(keyPath, sizeof(keyPath), gConfigNetwork.player_name);
if (!Platform::FileExists(keyPath))
if (!File::Exists(keyPath))
{
Console::WriteLine("Generating key... This may take a while");
Console::WriteLine("Need to collect enough entropy from the system");
@@ -1016,7 +1017,7 @@ void NetworkBase::LoadGroups()
safe_strcat_path(path, "groups.json", sizeof(path));
json_t jsonGroupConfig;
if (Platform::FileExists(path))
if (File::Exists(path))
{
try
{
@@ -2127,7 +2128,7 @@ void NetworkBase::Client_Handle_TOKEN(NetworkConnection& connection, NetworkPack
{
utf8 keyPath[MAX_PATH];
network_get_private_key_path(keyPath, sizeof(keyPath), gConfigNetwork.player_name);
if (!Platform::FileExists(keyPath))
if (!File::Exists(keyPath))
{
log_error("Key file (%s) was not found. Restart client to re-generate it.", keyPath);
return;
@@ -3842,7 +3843,7 @@ void network_send_password(const std::string& password)
auto& network = OpenRCT2::GetContext()->GetNetwork();
utf8 keyPath[MAX_PATH];
network_get_private_key_path(keyPath, sizeof(keyPath), gConfigNetwork.player_name);
if (!Platform::FileExists(keyPath))
if (!File::Exists(keyPath))
{
log_error("Private key %s missing! Restart the game to generate it.", keyPath);
return;

View File

@@ -12,6 +12,7 @@
# include "NetworkUser.h"
# include "../core/Console.hpp"
# include "../core/File.h"
# include "../core/Guard.hpp"
# include "../core/Json.hpp"
# include "../core/Path.hpp"
@@ -80,7 +81,7 @@ void NetworkUserManager::Load()
utf8 path[MAX_PATH];
GetStorePath(path, sizeof(path));
if (Platform::FileExists(path))
if (File::Exists(path))
{
DisposeUsers();
@@ -114,7 +115,7 @@ void NetworkUserManager::Save()
json_t jsonUsers;
try
{
if (Platform::FileExists(path))
if (File::Exists(path))
{
jsonUsers = Json::ReadFromFile(path);
}

View File

@@ -14,6 +14,7 @@
# include "../Context.h"
# include "../PlatformEnvironment.h"
# include "../config/Config.h"
# include "../core/File.h"
# include "../core/FileStream.h"
# include "../core/Guard.hpp"
# include "../core/Http.h"
@@ -162,7 +163,7 @@ std::vector<ServerListEntry> ServerList::ReadFavourites() const
{
auto env = GetContext()->GetPlatformEnvironment();
auto path = env->GetFilePath(PATHID::NETWORK_SERVERS);
if (Platform::FileExists(path))
if (File::Exists(path))
{
auto fs = FileStream(path, FILE_MODE_OPEN);
auto numEntries = fs.ReadValue<uint32_t>();

View File

@@ -25,6 +25,8 @@
# include <fontconfig/fontconfig.h>
# endif // NO_TTF
# include "../config/Config.h"
# include "../core/File.h"
# include "../core/Path.hpp"
# include "../localisation/Language.h"
# include "../localisation/StringIds.h"
# include "../util/Util.h"
@@ -70,7 +72,7 @@ bool platform_get_steam_path(utf8* outPath, size_t outSize)
{
safe_strcpy(steamPath, localSharePath, sizeof(steamPath));
safe_strcat_path(steamPath, "Steam/ubuntu12_32/steamapps/content", sizeof(steamPath));
if (platform_directory_exists(steamPath))
if (Path::DirectoryExists(steamPath))
{
safe_strcpy(outPath, steamPath, outSize);
return true;
@@ -82,7 +84,7 @@ bool platform_get_steam_path(utf8* outPath, size_t outSize)
{
safe_strcpy(steamPath, homeDir, sizeof(steamPath));
safe_strcat_path(steamPath, ".local/share/Steam/ubuntu12_32/steamapps/content", sizeof(steamPath));
if (platform_directory_exists(steamPath))
if (Path::DirectoryExists(steamPath))
{
safe_strcpy(outPath, steamPath, outSize);
return true;
@@ -91,7 +93,7 @@ bool platform_get_steam_path(utf8* outPath, size_t outSize)
std::fill_n(steamPath, sizeof(steamPath), 0x00);
safe_strcpy(steamPath, homeDir, sizeof(steamPath));
safe_strcat_path(steamPath, ".steam/steam/ubuntu12_32/steamapps/content", sizeof(steamPath));
if (platform_directory_exists(steamPath))
if (Path::DirectoryExists(steamPath))
{
safe_strcpy(outPath, steamPath, outSize);
return true;

View File

@@ -63,7 +63,7 @@ namespace Platform
for (auto searchLocation : searchLocations)
{
log_verbose("Looking for OpenRCT2 doc path at %s", searchLocation);
if (platform_directory_exists(searchLocation))
if (Path::DirectoryExists(searchLocation))
{
return searchLocation;
}

View File

@@ -267,80 +267,6 @@ namespace Platform
}
return result;
}
bool CopyFile(std::string_view srcPath, std::string_view dstPath, bool overwrite)
{
log_verbose("Copying %s to %s", std::string(srcPath).c_str(), std::string(dstPath).c_str());
FILE* dstFile;
if (overwrite)
{
dstFile = fopen(std::string(std::string(dstPath).c_str()).c_str(), "wb");
}
else
{
// Portability note: check your libc's support for "wbx"
dstFile = fopen(std::string(dstPath).c_str(), "wbx");
}
if (dstFile == nullptr)
{
if (errno == EEXIST)
{
log_warning(
"Platform::CopyFile(): Not overwriting %s, because overwrite flag == false", std::string(dstPath).c_str());
return false;
}
log_error("Could not open destination file %s for copying", std::string(dstPath).c_str());
return false;
}
// Open both files and check whether they are opened correctly
FILE* srcFile = fopen(std::string(srcPath).c_str(), "rb");
if (srcFile == nullptr)
{
fclose(dstFile);
log_error("Could not open source file %s for copying", std::string(srcPath).c_str());
return false;
}
size_t amount_read = 0;
size_t file_offset = 0;
// Copy file in FILE_BUFFER_SIZE-d chunks
char* buffer = static_cast<char*>(malloc(FILE_BUFFER_SIZE));
while ((amount_read = fread(buffer, FILE_BUFFER_SIZE, 1, srcFile)))
{
fwrite(buffer, amount_read, 1, dstFile);
file_offset += amount_read;
}
// Finish the left-over data from file, which may not be a full
// FILE_BUFFER_SIZE-d chunk.
fseek(srcFile, file_offset, SEEK_SET);
amount_read = fread(buffer, 1, FILE_BUFFER_SIZE, srcFile);
fwrite(buffer, amount_read, 1, dstFile);
fclose(srcFile);
fclose(dstFile);
free(buffer);
return true;
}
bool MoveFile(std::string_view srcPath, std::string_view dstPath)
{
return rename(std::string(srcPath).c_str(), std::string(dstPath).c_str()) == 0;
}
bool DeleteFile(std::string_view path)
{
int32_t ret = unlink(std::string(path).c_str());
return ret == 0;
}
} // namespace Platform
#endif

View File

@@ -707,29 +707,6 @@ namespace Platform
return Platform::GetCurrencyValue(currCode);
}
bool CopyFile(std::string_view srcPath, std::string_view dstPath, bool overwrite)
{
auto wSrcPath = String::ToWideChar(srcPath);
auto wDstPath = String::ToWideChar(dstPath);
auto success = CopyFileW(wSrcPath.c_str(), wDstPath.c_str(), overwrite ? FALSE : TRUE);
return success != FALSE;
}
bool MoveFile(std::string_view srcPath, std::string_view dstPath)
{
auto wSrcPath = String::ToWideChar(srcPath);
auto wDstPath = String::ToWideChar(dstPath);
auto success = MoveFileW(wSrcPath.c_str(), wDstPath.c_str());
return success != FALSE;
}
bool DeleteFile(std::string_view path)
{
auto wPath = String::ToWideChar(path);
auto success = DeleteFileW(wPath.c_str());
return success != FALSE;
}
} // namespace Platform
#endif

View File

@@ -35,16 +35,12 @@ namespace Platform
std::string GetCurrentExecutablePath();
std::string GetCurrentExecutableDirectory();
bool ShouldIgnoreCase();
bool FileExists(std::string_view path);
bool IsPathSeparator(char c);
utf8* GetAbsolutePath(utf8* buffer, size_t bufferSize, const utf8* relativePath);
uint64_t GetLastModified(std::string_view path);
uint64_t GetFileSize(std::string_view path);
std::string ResolveCasing(std::string_view path, bool fileExists);
std::string SanitiseFilename(std::string_view originalName);
bool CopyFile(std::string_view srcPath, std::string_view dstPath, bool overwrite);
bool MoveFile(std::string_view srcPath, std::string_view dstPath);
bool DeleteFile(std::string_view path);
uint16_t GetLocaleLanguage();
CurrencyType GetLocaleCurrency();

View File

@@ -40,14 +40,6 @@
static utf8 _userDataDirectoryPath[MAX_PATH] = { 0 };
bool platform_directory_exists(const utf8* path)
{
struct stat dirinfo;
int32_t result = stat(path, &dirinfo);
log_verbose("checking dir %s, result = %d, is_dir = %d", path, result, S_ISDIR(dirinfo.st_mode));
return result == 0 && S_ISDIR(dirinfo.st_mode);
}
// Implement our own version of getumask(), as it is documented being
// "a vaporware GNU extension".
static mode_t openrct2_getumask()

View File

@@ -19,6 +19,7 @@
#include "../Game.h"
#include "../OpenRCT2.h"
#include "../config/Config.h"
#include "../core/File.h"
#include "../core/FileSystem.hpp"
#include "../core/Path.hpp"
#include "../core/String.hpp"
@@ -113,17 +114,10 @@ namespace Platform
return outTime;
}
bool FileExists(std::string_view path)
{
fs::path file = u8path(path);
log_verbose("Checking if file exists: %s", std::string(path).c_str());
return fs::exists(file);
}
bool OriginalGameDataExists(std::string_view path)
{
std::string combinedPath = Path::ResolveCasing(Path::Combine(path, "Data", "g1.dat"));
return Platform::FileExists(combinedPath);
return File::Exists(combinedPath);
}
std::string SanitiseFilename(std::string_view originalName)

View File

@@ -25,6 +25,7 @@
# include "../OpenRCT2.h"
# include "../Version.h"
# include "../config/Config.h"
# include "../core/Path.hpp"
# include "../core/String.hpp"
# include "../localisation/Date.h"
# include "../localisation/Language.h"
@@ -59,16 +60,9 @@
# define swprintf_s(a, b, c, d, ...) swprintf(a, b, c, ##__VA_ARGS__)
# endif
bool platform_directory_exists(const utf8* path)
{
auto wPath = String::ToWideChar(path);
DWORD dwAttrib = GetFileAttributesW(wPath.c_str());
return dwAttrib != INVALID_FILE_ATTRIBUTES && (dwAttrib & FILE_ATTRIBUTE_DIRECTORY);
}
bool platform_ensure_directory_exists(const utf8* path)
{
if (platform_directory_exists(path))
if (Path::DirectoryExists(path))
return 1;
auto wPath = String::ToWideChar(path);

View File

@@ -10,6 +10,7 @@
#if defined(__APPLE__) && defined(__MACH__)
# include "../config/Config.h"
# include "../core/Path.hpp"
# include "../localisation/Language.h"
# include "../util/Util.h"
# include "platform.h"
@@ -69,7 +70,7 @@ bool platform_get_steam_path(utf8* outPath, size_t outSize)
safe_strcpy(steamPath, homeDir, sizeof(steamPath));
safe_strcat_path(
steamPath, "Library/Application Support/Steam/Steam.AppBundle/Steam/Contents/MacOS/steamapps", sizeof(steamPath));
if (platform_directory_exists(steamPath))
if (Path::DirectoryExists(steamPath))
{
safe_strcpy(outPath, steamPath, outSize);
return true;

View File

@@ -87,7 +87,6 @@ void platform_toggle_windowed_mode();
void platform_refresh_video(bool recreate_window);
// Platform specific definitions
bool platform_directory_exists(const utf8* path);
time_t platform_file_get_modified_time(const utf8* path);
bool platform_ensure_directory_exists(const utf8* path);
bool platform_directory_delete(const utf8* path);

View File

@@ -601,7 +601,7 @@ private:
void LoadScores()
{
std::string path = _env->GetFilePath(PATHID::SCORES);
if (!Platform::FileExists(path))
if (!File::Exists(path))
{
return;
}
@@ -648,7 +648,7 @@ private:
void LoadLegacyScores(const std::string& path)
{
if (!Platform::FileExists(path))
if (!File::Exists(path))
{
return;
}