From fbd72fd6bf0f02a13be207c9d61f630c594e3156 Mon Sep 17 00:00:00 2001 From: Emmanuel Gil Peyrot Date: Mon, 29 Sep 2014 08:34:37 +0000 Subject: Common: Add a helper function to generate a 8.3 filename from a long one. Core: Fix the SDMC Directory implementation to make blargSnes work. --- src/common/file_util.cpp | 42 ++++++++++++++++++++++++++++++++++++++++++ src/common/file_util.h | 11 +++++++++++ 2 files changed, 53 insertions(+) (limited to 'src/common') diff --git a/src/common/file_util.cpp b/src/common/file_util.cpp index 9292a1cd..5fd15522 100644 --- a/src/common/file_util.cpp +++ b/src/common/file_util.cpp @@ -780,6 +780,48 @@ size_t ReadFileToString(bool text_file, const char *filename, std::string &str) return file.ReadArray(&str[0], str.size()); } +/** + * Splits the filename into 8.3 format + * Loosely implemented following https://en.wikipedia.org/wiki/8.3_filename + * @param filename The normal filename to use + * @param short_name A 9-char array in which the short name will be written + * @param extension A 4-char array in which the extension will be written + */ +void SplitFilename83(const std::string& filename, std::array& short_name, + std::array& extension) { + const std::string forbidden_characters = ".\"/\\[]:;=, "; + + // On a FAT32 partition, 8.3 names are stored as a 11 bytes array, filled with spaces. + short_name = {' ', ' ', ' ', ' ', ' ', ' ', ' ', ' ', '\0'}; + extension = {' ', ' ', ' ', '\0'}; + + std::string::size_type point = filename.rfind('.'); + if (point == filename.size() - 1) + point = filename.rfind('.', point); + + // Get short name. + int j = 0; + for (char letter : filename.substr(0, point)) { + if (forbidden_characters.find(letter, 0) != std::string::npos) + continue; + if (j == 8) { + // TODO(Link Mauve): also do that for filenames containing a space. + // TODO(Link Mauve): handle multiple files having the same short name. + short_name[6] = '~'; + short_name[7] = '1'; + break; + } + short_name[j++] = toupper(letter); + } + + // Get extension. + if (point != std::string::npos) { + j = 0; + for (char letter : filename.substr(point + 1, 3)) + extension[j++] = toupper(letter); + } +} + IOFile::IOFile() : m_file(NULL), m_good(true) {} diff --git a/src/common/file_util.h b/src/common/file_util.h index f9d91972..288734ca 100644 --- a/src/common/file_util.h +++ b/src/common/file_util.h @@ -4,6 +4,7 @@ #pragma once +#include #include #include #include @@ -131,6 +132,16 @@ std::string &GetExeDirectory(); size_t WriteStringToFile(bool text_file, const std::string &str, const char *filename); size_t ReadFileToString(bool text_file, const char *filename, std::string &str); +/** + * Splits the filename into 8.3 format + * Loosely implemented following https://en.wikipedia.org/wiki/8.3_filename + * @param filename The normal filename to use + * @param short_name A 9-char array in which the short name will be written + * @param extension A 4-char array in which the extension will be written + */ +void SplitFilename83(const std::string& filename, std::array& short_name, + std::array& extension); + // simple wrapper for cstdlib file functions to // hopefully will make error checking easier // and make forgetting an fclose() harder -- cgit v1.2.3