mirror of
https://github.com/jorio/Pomme.git
synced 2025-02-19 20:30:33 +00:00
Use u8string for all filesystem paths
This commit is contained in:
parent
9fae17d771
commit
b8d624facd
@ -112,7 +112,9 @@ OSErr FSMakeFSSpec(short vRefNum, long dirID, const char* cstrFileName, FSSpec*
|
|||||||
if (!IsVolumeLegal(vRefNum))
|
if (!IsVolumeLegal(vRefNum))
|
||||||
return nsvErr;
|
return nsvErr;
|
||||||
|
|
||||||
return volumes.at(vRefNum)->FSMakeFSSpec(dirID, cstrFileName, spec);
|
u8string fileName((const char8_t*)cstrFileName);
|
||||||
|
|
||||||
|
return volumes.at(vRefNum)->FSMakeFSSpec(dirID, fileName, spec);
|
||||||
}
|
}
|
||||||
|
|
||||||
static OSErr OpenFork(const FSSpec* spec, ForkType forkType, char permission, short* refNum)
|
static OSErr OpenFork(const FSSpec* spec, ForkType forkType, char permission, short* refNum)
|
||||||
@ -165,7 +167,7 @@ OSErr FindFolder(short vRefNum, OSType folderType, Boolean createFolder, short*
|
|||||||
throw std::runtime_error("FindFolder only supports kOnSystemDisk");
|
throw std::runtime_error("FindFolder only supports kOnSystemDisk");
|
||||||
}
|
}
|
||||||
|
|
||||||
fs::path path;
|
fs::path path = "";
|
||||||
|
|
||||||
switch (folderType)
|
switch (folderType)
|
||||||
{
|
{
|
||||||
@ -175,7 +177,8 @@ OSErr FindFolder(short vRefNum, OSType folderType, Boolean createFolder, short*
|
|||||||
path = Pomme::Platform::Windows::GetPreferencesFolder();
|
path = Pomme::Platform::Windows::GetPreferencesFolder();
|
||||||
#elif defined(__APPLE__)
|
#elif defined(__APPLE__)
|
||||||
const char *home = getenv("HOME");
|
const char *home = getenv("HOME");
|
||||||
if (!home) {
|
if (!home)
|
||||||
|
{
|
||||||
return fnfErr;
|
return fnfErr;
|
||||||
}
|
}
|
||||||
path = fs::path(home) / "Library" / "Preferences";
|
path = fs::path(home) / "Library" / "Preferences";
|
||||||
@ -203,6 +206,11 @@ OSErr FindFolder(short vRefNum, OSType folderType, Boolean createFolder, short*
|
|||||||
return fnfErr;
|
return fnfErr;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (path.empty())
|
||||||
|
{
|
||||||
|
return fnfErr;
|
||||||
|
}
|
||||||
|
|
||||||
path = path.lexically_normal();
|
path = path.lexically_normal();
|
||||||
|
|
||||||
bool exists = fs::exists(path);
|
bool exists = fs::exists(path);
|
||||||
@ -223,9 +231,15 @@ OSErr FindFolder(short vRefNum, OSType folderType, Boolean createFolder, short*
|
|||||||
|
|
||||||
OSErr DirCreate(short vRefNum, long parentDirID, const char* cstrDirectoryName, long* createdDirID)
|
OSErr DirCreate(short vRefNum, long parentDirID, const char* cstrDirectoryName, long* createdDirID)
|
||||||
{
|
{
|
||||||
return IsVolumeLegal(vRefNum)
|
if (!IsVolumeLegal(vRefNum))
|
||||||
? volumes.at(vRefNum)->DirCreate(parentDirID, cstrDirectoryName, createdDirID)
|
{
|
||||||
: (OSErr)nsvErr;
|
return (OSErr)nsvErr;
|
||||||
|
}
|
||||||
|
|
||||||
|
u8string directoryName((const char8_t*)cstrDirectoryName);
|
||||||
|
|
||||||
|
const auto& volume = volumes.at(vRefNum);
|
||||||
|
return volume->DirCreate(parentDirID, directoryName, createdDirID);
|
||||||
}
|
}
|
||||||
|
|
||||||
OSErr FSpCreate(const FSSpec* spec, OSType creator, OSType fileType, ScriptCode scriptTag)
|
OSErr FSpCreate(const FSSpec* spec, OSType creator, OSType fileType, ScriptCode scriptTag)
|
||||||
|
@ -68,9 +68,15 @@ long HostVolume::GetDirectoryID(const fs::path& dirPath)
|
|||||||
//-----------------------------------------------------------------------------
|
//-----------------------------------------------------------------------------
|
||||||
// Internal utilities
|
// Internal utilities
|
||||||
|
|
||||||
fs::path HostVolume::ToPath(long parID, const std::string& name)
|
fs::path HostVolume::ToPath(long parID, const char* name)
|
||||||
{
|
{
|
||||||
fs::path path = directories.at(parID) / AsU8(name);
|
return ToPath(parID, u8string((const char8_t*)name));
|
||||||
|
}
|
||||||
|
|
||||||
|
fs::path HostVolume::ToPath(long parID, const u8string& name)
|
||||||
|
{
|
||||||
|
fs::path path = directories.at(parID);
|
||||||
|
path /= name;
|
||||||
return path.lexically_normal();
|
return path.lexically_normal();
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -161,12 +167,9 @@ OSErr HostVolume::OpenFork(const FSSpec* spec, ForkType forkType, char permissio
|
|||||||
return noErr;
|
return noErr;
|
||||||
}
|
}
|
||||||
|
|
||||||
static bool CaseInsensitiveAppendToPath(
|
static bool CaseInsensitiveAppendToPath(fs::path& path, const u8string& element, bool skipFiles = false)
|
||||||
fs::path& path,
|
|
||||||
const std::string& element,
|
|
||||||
bool skipFiles = false)
|
|
||||||
{
|
{
|
||||||
fs::path naiveConcat = path / AsU8(element);
|
fs::path naiveConcat = path / element;
|
||||||
|
|
||||||
if (!fs::exists(path))
|
if (!fs::exists(path))
|
||||||
{
|
{
|
||||||
@ -199,11 +202,7 @@ static bool CaseInsensitiveAppendToPath(
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Convert candidate filename to uppercase for case-insensitive comparison
|
// Convert candidate filename to uppercase for case-insensitive comparison
|
||||||
#if LEGACY_FILESYSTEM_IMPLEMENTATION // ghc::path::u8string returns an std::string
|
const u8string uppercaseCandidateFilename = UppercaseCopy(candidateFilename.u8string());
|
||||||
const std::string uppercaseCandidateFilename = UppercaseCopy(candidateFilename.u8string());
|
|
||||||
#else // C++20
|
|
||||||
const std::string uppercaseCandidateFilename = UppercaseCopy(FromU8(candidateFilename.u8string()));
|
|
||||||
#endif
|
|
||||||
|
|
||||||
if (uppercaseElement == uppercaseCandidateFilename)
|
if (uppercaseElement == uppercaseCandidateFilename)
|
||||||
{
|
{
|
||||||
@ -219,7 +218,7 @@ static bool CaseInsensitiveAppendToPath(
|
|||||||
//-----------------------------------------------------------------------------
|
//-----------------------------------------------------------------------------
|
||||||
// Implementation
|
// Implementation
|
||||||
|
|
||||||
OSErr HostVolume::FSMakeFSSpec(long dirID, const std::string& fileName, FSSpec* spec)
|
OSErr HostVolume::FSMakeFSSpec(long dirID, const u8string& fileName, FSSpec* spec)
|
||||||
{
|
{
|
||||||
if (dirID < 0 || (unsigned long) dirID >= directories.size())
|
if (dirID < 0 || (unsigned long) dirID >= directories.size())
|
||||||
{
|
{
|
||||||
@ -231,12 +230,12 @@ OSErr HostVolume::FSMakeFSSpec(long dirID, const std::string& fileName, FSSpec*
|
|||||||
|
|
||||||
// Case-insensitive sanitization
|
// Case-insensitive sanitization
|
||||||
bool exists = fs::exists(path);
|
bool exists = fs::exists(path);
|
||||||
std::string::size_type begin = (suffix.at(0) == ':') ? 1 : 0;
|
u8string::size_type begin = (suffix.at(0) == ':') ? 1 : 0;
|
||||||
|
|
||||||
// Iterate on path elements between colons
|
// Iterate on path elements between colons
|
||||||
while (begin < suffix.length())
|
while (begin < suffix.length())
|
||||||
{
|
{
|
||||||
auto end = suffix.find(":", begin);
|
auto end = suffix.find(':', begin);
|
||||||
|
|
||||||
bool isLeaf = end == std::string::npos; // no ':' found => end of path
|
bool isLeaf = end == std::string::npos; // no ':' found => end of path
|
||||||
if (isLeaf) end = suffix.length();
|
if (isLeaf) end = suffix.length();
|
||||||
@ -264,7 +263,7 @@ OSErr HostVolume::FSMakeFSSpec(long dirID, const std::string& fileName, FSSpec*
|
|||||||
return exists ? noErr : fnfErr;
|
return exists ? noErr : fnfErr;
|
||||||
}
|
}
|
||||||
|
|
||||||
OSErr HostVolume::DirCreate(long parentDirID, const std::string& directoryName, long* createdDirID)
|
OSErr HostVolume::DirCreate(long parentDirID, const u8string& directoryName, long* createdDirID)
|
||||||
{
|
{
|
||||||
const auto path = ToPath(parentDirID, directoryName);
|
const auto path = ToPath(parentDirID, directoryName);
|
||||||
|
|
||||||
|
@ -2,6 +2,7 @@
|
|||||||
|
|
||||||
#include "Files/Volume.h"
|
#include "Files/Volume.h"
|
||||||
#include "CompilerSupport/filesystem.h"
|
#include "CompilerSupport/filesystem.h"
|
||||||
|
#include "Utilities/StringUtils.h"
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
||||||
namespace Pomme::Files
|
namespace Pomme::Files
|
||||||
@ -14,7 +15,8 @@ namespace Pomme::Files
|
|||||||
{
|
{
|
||||||
std::vector<fs::path> directories;
|
std::vector<fs::path> directories;
|
||||||
|
|
||||||
fs::path ToPath(long parID, const std::string& name);
|
fs::path ToPath(long parID, const char* name);
|
||||||
|
fs::path ToPath(long parID, const u8string& name);
|
||||||
|
|
||||||
public:
|
public:
|
||||||
explicit HostVolume(short vRefNum);
|
explicit HostVolume(short vRefNum);
|
||||||
@ -31,7 +33,7 @@ namespace Pomme::Files
|
|||||||
//-----------------------------------------------------------------------------
|
//-----------------------------------------------------------------------------
|
||||||
// Toolbox API Implementation
|
// Toolbox API Implementation
|
||||||
|
|
||||||
OSErr FSMakeFSSpec(long dirID, const std::string& fileName, FSSpec* spec) override;
|
OSErr FSMakeFSSpec(long dirID, const u8string& fileName, FSSpec* spec) override;
|
||||||
|
|
||||||
OSErr OpenFork(const FSSpec* spec, ForkType forkType, char permission, std::unique_ptr<ForkHandle>& stream) override;
|
OSErr OpenFork(const FSSpec* spec, ForkType forkType, char permission, std::unique_ptr<ForkHandle>& stream) override;
|
||||||
|
|
||||||
@ -39,6 +41,6 @@ namespace Pomme::Files
|
|||||||
|
|
||||||
OSErr FSpDelete(const FSSpec* spec) override;
|
OSErr FSpDelete(const FSSpec* spec) override;
|
||||||
|
|
||||||
OSErr DirCreate(long parentDirID, const std::string& directoryName, long* createdDirID) override;
|
OSErr DirCreate(long parentDirID, const u8string& directoryName, long* createdDirID) override;
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include <memory>
|
#include <memory>
|
||||||
|
#include "Utilities/StringUtils.h"
|
||||||
|
|
||||||
namespace Pomme::Files
|
namespace Pomme::Files
|
||||||
{
|
{
|
||||||
@ -48,7 +49,7 @@ namespace Pomme::Files
|
|||||||
//-----------------------------------------------------------------------------
|
//-----------------------------------------------------------------------------
|
||||||
// Toolbox API Implementation
|
// Toolbox API Implementation
|
||||||
|
|
||||||
virtual OSErr FSMakeFSSpec(long dirID, const std::string& suffix, FSSpec* spec) = 0;
|
virtual OSErr FSMakeFSSpec(long dirID, const u8string& suffix, FSSpec* spec) = 0;
|
||||||
|
|
||||||
virtual OSErr OpenFork(const FSSpec* spec, ForkType forkType, char permission, std::unique_ptr<ForkHandle>& handle) = 0;
|
virtual OSErr OpenFork(const FSSpec* spec, ForkType forkType, char permission, std::unique_ptr<ForkHandle>& handle) = 0;
|
||||||
|
|
||||||
@ -56,6 +57,6 @@ namespace Pomme::Files
|
|||||||
|
|
||||||
virtual OSErr FSpDelete(const FSSpec* spec) = 0;
|
virtual OSErr FSpDelete(const FSSpec* spec) = 0;
|
||||||
|
|
||||||
virtual OSErr DirCreate(long parentDirID, const std::string& directoryName, long* createdDirID) = 0;
|
virtual OSErr DirCreate(long parentDirID, const u8string& directoryName, long* createdDirID) = 0;
|
||||||
};
|
};
|
||||||
}
|
}
|
@ -1,14 +1,22 @@
|
|||||||
#undef NOUSER
|
#undef NOUSER
|
||||||
|
|
||||||
|
#include "PommeDebug.h"
|
||||||
#include "Platform/Windows/PommeWindows.h"
|
#include "Platform/Windows/PommeWindows.h"
|
||||||
|
|
||||||
#include <shlobj.h>
|
#include <shlobj.h>
|
||||||
|
|
||||||
std::filesystem::path Pomme::Platform::Windows::GetPreferencesFolder()
|
std::filesystem::path Pomme::Platform::Windows::GetPreferencesFolder()
|
||||||
{
|
{
|
||||||
wchar_t* wpath = nullptr;
|
PWSTR wpath = nullptr;
|
||||||
SHGetKnownFolderPath(FOLDERID_RoamingAppData, 0, nullptr, &wpath);
|
HRESULT result = SHGetKnownFolderPath(FOLDERID_RoamingAppData, 0, nullptr, &wpath);
|
||||||
auto path = std::filesystem::path(wpath);
|
|
||||||
|
std::filesystem::path path = "";
|
||||||
|
|
||||||
|
if (result == S_OK)
|
||||||
|
{
|
||||||
|
path = std::filesystem::path(wpath);
|
||||||
|
}
|
||||||
|
|
||||||
CoTaskMemFree(static_cast<void*>(wpath));
|
CoTaskMemFree(static_cast<void*>(wpath));
|
||||||
return path;
|
return path;
|
||||||
}
|
}
|
||||||
|
@ -268,8 +268,9 @@ SndListHandle Pomme_SndLoadFileAsResource(short fRefNum)
|
|||||||
auto& spec = Pomme::Files::GetSpec(fRefNum);
|
auto& spec = Pomme::Files::GetSpec(fRefNum);
|
||||||
auto& stream = Pomme::Files::GetStream(fRefNum);
|
auto& stream = Pomme::Files::GetStream(fRefNum);
|
||||||
|
|
||||||
std::string fileName = UppercaseCopy(spec.cName);
|
u8string fileName((const char8_t*) spec.cName);
|
||||||
fs::path extension = fs::path(AsU8(fileName)).extension();
|
fileName = UppercaseCopy(fileName);
|
||||||
|
fs::path extension = fs::path(fileName).extension();
|
||||||
|
|
||||||
// Guess media container from extension
|
// Guess media container from extension
|
||||||
if (extension == ".AIFF"
|
if (extension == ".AIFF"
|
||||||
|
@ -3,9 +3,9 @@
|
|||||||
#include <algorithm>
|
#include <algorithm>
|
||||||
#include <iterator>
|
#include <iterator>
|
||||||
|
|
||||||
std::string UppercaseCopy(const std::string& in)
|
std::u8string UppercaseCopy(const u8string& in)
|
||||||
{
|
{
|
||||||
std::string out;
|
std::u8string out;
|
||||||
std::transform(
|
std::transform(
|
||||||
in.begin(),
|
in.begin(),
|
||||||
in.end(),
|
in.end(),
|
||||||
@ -16,13 +16,3 @@ std::string UppercaseCopy(const std::string& in)
|
|||||||
});
|
});
|
||||||
return out;
|
return out;
|
||||||
}
|
}
|
||||||
|
|
||||||
u8string AsU8(const std::string s)
|
|
||||||
{
|
|
||||||
return u8string(s.begin(), s.end());
|
|
||||||
}
|
|
||||||
|
|
||||||
std::string FromU8(const u8string u8s)
|
|
||||||
{
|
|
||||||
return std::string(u8s.begin(), u8s.end());
|
|
||||||
}
|
|
||||||
|
@ -6,10 +6,7 @@
|
|||||||
typedef std::u8string u8string;
|
typedef std::u8string u8string;
|
||||||
#else
|
#else
|
||||||
typedef std::string u8string;
|
typedef std::string u8string;
|
||||||
|
typedef char char8_t;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
std::string UppercaseCopy(const std::string&);
|
u8string UppercaseCopy(const u8string&);
|
||||||
|
|
||||||
u8string AsU8(const std::string);
|
|
||||||
|
|
||||||
std::string FromU8(const u8string);
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user