FileSystem: Add IsValidFileName()

And associated tests.
This commit is contained in:
Stenzek 2023-07-04 20:56:13 +10:00 committed by Connor McLaughlin
parent 5057dfedba
commit a9a1af7307
3 changed files with 47 additions and 0 deletions

View File

@ -190,6 +190,27 @@ void Path::SanitizeFileName(std::string* str, bool strip_slashes /* = true */)
#endif #endif
} }
bool Path::IsValidFileName(const std::string_view& str, bool allow_slashes)
{
const size_t len = str.length();
size_t pos = 0;
while (pos < len)
{
char32_t ch;
pos += StringUtil::DecodeUTF8(str.data() + pos, pos - len, &ch);
if (!FileSystemCharacterIsSane(ch, !allow_slashes))
return false;
}
#ifdef _WIN32
// Windows: Can't end filename with a period.
if (len > 0 && str.back() == '.')
return false;
#endif
return true;
}
bool Path::IsAbsolute(const std::string_view& path) bool Path::IsAbsolute(const std::string_view& path)
{ {
#ifdef _WIN32 #ifdef _WIN32

View File

@ -41,6 +41,9 @@ namespace Path
std::string SanitizeFileName(const std::string_view& str, bool strip_slashes = true); std::string SanitizeFileName(const std::string_view& str, bool strip_slashes = true);
void SanitizeFileName(std::string* str, bool strip_slashes = true); void SanitizeFileName(std::string* str, bool strip_slashes = true);
/// Returns true if the specified filename is valid on this operating system.
bool IsValidFileName(const std::string_view& str, bool allow_slashes = false);
/// Returns true if the specified path is an absolute path (C:\Path on Windows or /path on Unix). /// Returns true if the specified path is an absolute path (C:\Path on Windows or /path on Unix).
bool IsAbsolute(const std::string_view& path); bool IsAbsolute(const std::string_view& path);

View File

@ -41,6 +41,29 @@ TEST(FileSystem, ToNativePath)
#endif #endif
} }
TEST(FileSystem, IsValidFileName)
{
#if defined(_WIN32) || defined(__APPLE__)
ASSERT_FALSE(Path::IsValidFileName("foo:bar", false));
ASSERT_FALSE(Path::IsValidFileName("baz\\foo:bar", false));
ASSERT_FALSE(Path::IsValidFileName("baz/foo:bar", false));
ASSERT_FALSE(Path::IsValidFileName("baz\\foo:bar", true));
ASSERT_FALSE(Path::IsValidFileName("baz/foo:bar", true));
#endif
#ifdef _WIN32
ASSERT_TRUE(Path::IsValidFileName("baz\\foo", true));
ASSERT_FALSE(Path::IsValidFileName("baz\\foo", false));
ASSERT_FALSE(Path::IsValidFileName("foo.", true));
ASSERT_FALSE(Path::IsValidFileName("foo\\.", true));
#else
ASSERT_FALSE(Path::IsValidFileName("foo\\*", true));
ASSERT_FALSE(Path::IsValidFileName("foo*", true));
#endif
ASSERT_TRUE(Path::IsValidFileName("baz/foo", true));
ASSERT_FALSE(Path::IsValidFileName("baz/foo", false));
}
TEST(FileSystem, IsAbsolute) TEST(FileSystem, IsAbsolute)
{ {
ASSERT_FALSE(Path::IsAbsolute("")); ASSERT_FALSE(Path::IsAbsolute(""));