diff options
Diffstat (limited to 'src/core/hle')
-rw-r--r-- | src/core/hle/result.h | 6 | ||||
-rw-r--r-- | src/core/hle/service/fs/archive.cpp | 191 | ||||
-rw-r--r-- | src/core/hle/service/fs/archive.h | 45 | ||||
-rw-r--r-- | src/core/hle/service/fs/fs_user.cpp | 10 | ||||
-rw-r--r-- | src/core/hle/service/ptm_u.cpp | 35 |
5 files changed, 140 insertions, 147 deletions
diff --git a/src/core/hle/result.h b/src/core/hle/result.h index 948b9e38e..9c6ca29e5 100644 --- a/src/core/hle/result.h +++ b/src/core/hle/result.h @@ -307,14 +307,14 @@ public: } ResultVal& operator=(const ResultVal& o) { - if (*this) { - if (o) { + if (!empty()) { + if (!o.empty()) { *GetPointer() = *o.GetPointer(); } else { GetPointer()->~T(); } } else { - if (o) { + if (!o.empty()) { new (&storage) T(*o.GetPointer()); } } diff --git a/src/core/hle/service/fs/archive.cpp b/src/core/hle/service/fs/archive.cpp index ccf132f31..e197d3599 100644 --- a/src/core/hle/service/fs/archive.cpp +++ b/src/core/hle/service/fs/archive.cpp @@ -5,6 +5,8 @@ #include <memory> #include <unordered_map> +#include <boost/container/flat_map.hpp> + #include "common/common_types.h" #include "common/file_util.h" #include "common/make_unique.h" @@ -18,7 +20,6 @@ #include "core/file_sys/archive_sdmc.h" #include "core/file_sys/directory_backend.h" #include "core/hle/service/fs/archive.h" -#include "core/hle/kernel/session.h" #include "core/hle/result.h" // Specializes std::hash for ArchiveIdCode, so that we can use it in std::unordered_map. @@ -74,43 +75,19 @@ enum class DirectoryCommand : u32 { Close = 0x08020000, }; -class Archive { -public: - Archive(std::unique_ptr<FileSys::ArchiveBackend>&& backend, ArchiveIdCode id_code) - : id_code(id_code), backend(std::move(backend)) { - } - - std::string GetName() const { return "Archive: " + backend->GetName(); } - - ArchiveIdCode id_code; ///< Id code of the archive - std::unique_ptr<FileSys::ArchiveBackend> backend; ///< Archive backend interface -}; - -class File : public Kernel::Session { -public: - File(std::unique_ptr<FileSys::FileBackend>&& backend, const FileSys::Path& path) - : path(path), priority(0), backend(std::move(backend)) { - } - - std::string GetName() const override { return "Path: " + path.DebugStr(); } - - FileSys::Path path; ///< Path of the file - u32 priority; ///< Priority of the file. TODO(Subv): Find out what this means - std::unique_ptr<FileSys::FileBackend> backend; ///< File backend interface - - ResultVal<bool> SyncRequest() override { - u32* cmd_buff = Kernel::GetCommandBuffer(); - FileCommand cmd = static_cast<FileCommand>(cmd_buff[0]); - switch (cmd) { +ResultVal<bool> File::SyncRequest() { + u32* cmd_buff = Kernel::GetCommandBuffer(); + FileCommand cmd = static_cast<FileCommand>(cmd_buff[0]); + switch (cmd) { // Read from file... case FileCommand::Read: { - u64 offset = cmd_buff[1] | ((u64) cmd_buff[2]) << 32; - u32 length = cmd_buff[3]; + u64 offset = cmd_buff[1] | ((u64)cmd_buff[2]) << 32; + u32 length = cmd_buff[3]; u32 address = cmd_buff[5]; LOG_TRACE(Service_FS, "Read %s %s: offset=0x%llx length=%d address=0x%x", - GetTypeName().c_str(), GetName().c_str(), offset, length, address); + GetTypeName().c_str(), GetName().c_str(), offset, length, address); cmd_buff[2] = backend->Read(offset, length, Memory::GetPointer(address)); break; } @@ -118,12 +95,12 @@ public: // Write to file... case FileCommand::Write: { - u64 offset = cmd_buff[1] | ((u64) cmd_buff[2]) << 32; - u32 length = cmd_buff[3]; - u32 flush = cmd_buff[4]; + u64 offset = cmd_buff[1] | ((u64)cmd_buff[2]) << 32; + u32 length = cmd_buff[3]; + u32 flush = cmd_buff[4]; u32 address = cmd_buff[6]; LOG_TRACE(Service_FS, "Write %s %s: offset=0x%llx length=%d address=0x%x, flush=0x%x", - GetTypeName().c_str(), GetName().c_str(), offset, length, address, flush); + GetTypeName().c_str(), GetName().c_str(), offset, length, address, flush); cmd_buff[2] = backend->Write(offset, length, flush, Memory::GetPointer(address)); break; } @@ -141,7 +118,7 @@ public: { u64 size = cmd_buff[1] | ((u64)cmd_buff[2] << 32); LOG_TRACE(Service_FS, "SetSize %s %s size=%llu", - GetTypeName().c_str(), GetName().c_str(), size); + GetTypeName().c_str(), GetName().c_str(), size); backend->SetSize(size); break; } @@ -187,27 +164,15 @@ public: ResultCode error = UnimplementedFunction(ErrorModule::FS); cmd_buff[1] = error.raw; // TODO(Link Mauve): use the correct error code for that. return error; - } - cmd_buff[1] = 0; // No error - return MakeResult<bool>(false); } -}; - -class Directory : public Kernel::Session { -public: - Directory(std::unique_ptr<FileSys::DirectoryBackend>&& backend, const FileSys::Path& path) - : path(path), backend(std::move(backend)) { - } - - std::string GetName() const override { return "Directory: " + path.DebugStr(); } - - FileSys::Path path; ///< Path of the directory - std::unique_ptr<FileSys::DirectoryBackend> backend; ///< File backend interface + cmd_buff[1] = RESULT_SUCCESS.raw; // No error + return MakeResult<bool>(false); +} - ResultVal<bool> SyncRequest() override { - u32* cmd_buff = Kernel::GetCommandBuffer(); - DirectoryCommand cmd = static_cast<DirectoryCommand>(cmd_buff[0]); - switch (cmd) { +ResultVal<bool> Directory::SyncRequest() { + u32* cmd_buff = Kernel::GetCommandBuffer(); + DirectoryCommand cmd = static_cast<DirectoryCommand>(cmd_buff[0]); + switch (cmd) { // Read from directory... case DirectoryCommand::Read: @@ -216,7 +181,7 @@ public: u32 address = cmd_buff[3]; auto entries = reinterpret_cast<FileSys::Entry*>(Memory::GetPointer(address)); LOG_TRACE(Service_FS, "Read %s %s: count=%d", - GetTypeName().c_str(), GetName().c_str(), count); + GetTypeName().c_str(), GetName().c_str(), count); // Number of entries actually read cmd_buff[2] = backend->Read(count, entries); @@ -236,29 +201,31 @@ public: ResultCode error = UnimplementedFunction(ErrorModule::FS); cmd_buff[1] = error.raw; // TODO(Link Mauve): use the correct error code for that. return MakeResult<bool>(false); - } - cmd_buff[1] = 0; // No error - return MakeResult<bool>(false); } -}; + cmd_buff[1] = RESULT_SUCCESS.raw; // No error + return MakeResult<bool>(false); +} //////////////////////////////////////////////////////////////////////////////////////////////////// +using FileSys::ArchiveBackend; +using FileSys::ArchiveFactory; + /** * Map of registered archives, identified by id code. Once an archive is registered here, it is * never removed until the FS service is shut down. */ -static std::unordered_map<ArchiveIdCode, std::unique_ptr<Archive>> id_code_map; +static boost::container::flat_map<ArchiveIdCode, std::unique_ptr<ArchiveFactory>> id_code_map; /** * Map of active archive handles. Values are pointers to the archives in `idcode_map`. */ -static std::unordered_map<ArchiveHandle, Archive*> handle_map; +static std::unordered_map<ArchiveHandle, std::unique_ptr<ArchiveBackend>> handle_map; static ArchiveHandle next_handle; -static Archive* GetArchive(ArchiveHandle handle) { +static ArchiveBackend* GetArchive(ArchiveHandle handle) { auto itr = handle_map.find(handle); - return (itr == handle_map.end()) ? nullptr : itr->second; + return (itr == handle_map.end()) ? nullptr : itr->second.get(); } ResultVal<ArchiveHandle> OpenArchive(ArchiveIdCode id_code, FileSys::Path& archive_path) { @@ -271,15 +238,13 @@ ResultVal<ArchiveHandle> OpenArchive(ArchiveIdCode id_code, FileSys::Path& archi ErrorSummary::NotFound, ErrorLevel::Permanent); } - ResultCode res = itr->second->backend->Open(archive_path); - if (!res.IsSuccess()) - return res; + CASCADE_RESULT(std::unique_ptr<ArchiveBackend> res, itr->second->Open(archive_path)); // This should never even happen in the first place with 64-bit handles, while (handle_map.count(next_handle) != 0) { ++next_handle; } - handle_map.emplace(next_handle, itr->second.get()); + handle_map.emplace(next_handle, std::move(res)); return MakeResult<ArchiveHandle>(next_handle++); } @@ -292,39 +257,39 @@ ResultCode CloseArchive(ArchiveHandle handle) { // TODO(yuriks): This might be what the fs:REG service is for. See the Register/Unregister calls in // http://3dbrew.org/wiki/Filesystem_services#ProgramRegistry_service_.22fs:REG.22 -ResultCode CreateArchive(std::unique_ptr<FileSys::ArchiveBackend>&& backend, ArchiveIdCode id_code) { - auto result = id_code_map.emplace(id_code, Common::make_unique<Archive>(std::move(backend), id_code)); +ResultCode RegisterArchiveType(std::unique_ptr<FileSys::ArchiveFactory>&& factory, ArchiveIdCode id_code) { + auto result = id_code_map.emplace(id_code, std::move(factory)); bool inserted = result.second; - _dbg_assert_msg_(Service_FS, inserted, "Tried to register more than one archive with same id code"); + _assert_msg_(Service_FS, inserted, "Tried to register more than one archive with same id code"); auto& archive = result.first->second; LOG_DEBUG(Service_FS, "Registered archive %s with id code 0x%08X", archive->GetName().c_str(), id_code); return RESULT_SUCCESS; } -ResultVal<Kernel::SharedPtr<Kernel::Session>> OpenFileFromArchive(ArchiveHandle archive_handle, +ResultVal<Kernel::SharedPtr<File>> OpenFileFromArchive(ArchiveHandle archive_handle, const FileSys::Path& path, const FileSys::Mode mode) { - Archive* archive = GetArchive(archive_handle); + ArchiveBackend* archive = GetArchive(archive_handle); if (archive == nullptr) return ERR_INVALID_HANDLE; - std::unique_ptr<FileSys::FileBackend> backend = archive->backend->OpenFile(path, mode); + std::unique_ptr<FileSys::FileBackend> backend = archive->OpenFile(path, mode); if (backend == nullptr) { return ResultCode(ErrorDescription::FS_NotFound, ErrorModule::FS, ErrorSummary::NotFound, ErrorLevel::Status); } auto file = Kernel::SharedPtr<File>(new File(std::move(backend), path)); - return MakeResult<Kernel::SharedPtr<Kernel::Session>>(std::move(file)); + return MakeResult<Kernel::SharedPtr<File>>(std::move(file)); } ResultCode DeleteFileFromArchive(ArchiveHandle archive_handle, const FileSys::Path& path) { - Archive* archive = GetArchive(archive_handle); + ArchiveBackend* archive = GetArchive(archive_handle); if (archive == nullptr) return ERR_INVALID_HANDLE; - if (archive->backend->DeleteFile(path)) + if (archive->DeleteFile(path)) return RESULT_SUCCESS; return ResultCode(ErrorDescription::NoData, ErrorModule::FS, // TODO: verify description ErrorSummary::Canceled, ErrorLevel::Status); @@ -332,13 +297,13 @@ ResultCode DeleteFileFromArchive(ArchiveHandle archive_handle, const FileSys::Pa ResultCode RenameFileBetweenArchives(ArchiveHandle src_archive_handle, const FileSys::Path& src_path, ArchiveHandle dest_archive_handle, const FileSys::Path& dest_path) { - Archive* src_archive = GetArchive(src_archive_handle); - Archive* dest_archive = GetArchive(dest_archive_handle); + ArchiveBackend* src_archive = GetArchive(src_archive_handle); + ArchiveBackend* dest_archive = GetArchive(dest_archive_handle); if (src_archive == nullptr || dest_archive == nullptr) return ERR_INVALID_HANDLE; if (src_archive == dest_archive) { - if (src_archive->backend->RenameFile(src_path, dest_path)) + if (src_archive->RenameFile(src_path, dest_path)) return RESULT_SUCCESS; } else { // TODO: Implement renaming across archives @@ -352,30 +317,30 @@ ResultCode RenameFileBetweenArchives(ArchiveHandle src_archive_handle, const Fil } ResultCode DeleteDirectoryFromArchive(ArchiveHandle archive_handle, const FileSys::Path& path) { - Archive* archive = GetArchive(archive_handle); + ArchiveBackend* archive = GetArchive(archive_handle); if (archive == nullptr) return ERR_INVALID_HANDLE; - if (archive->backend->DeleteDirectory(path)) + if (archive->DeleteDirectory(path)) return RESULT_SUCCESS; return ResultCode(ErrorDescription::NoData, ErrorModule::FS, // TODO: verify description ErrorSummary::Canceled, ErrorLevel::Status); } ResultCode CreateFileInArchive(ArchiveHandle archive_handle, const FileSys::Path& path, u32 file_size) { - Archive* archive = GetArchive(archive_handle); + ArchiveBackend* archive = GetArchive(archive_handle); if (archive == nullptr) return ERR_INVALID_HANDLE; - return archive->backend->CreateFile(path, file_size); + return archive->CreateFile(path, file_size); } ResultCode CreateDirectoryFromArchive(ArchiveHandle archive_handle, const FileSys::Path& path) { - Archive* archive = GetArchive(archive_handle); + ArchiveBackend* archive = GetArchive(archive_handle); if (archive == nullptr) return ERR_INVALID_HANDLE; - if (archive->backend->CreateDirectory(path)) + if (archive->CreateDirectory(path)) return RESULT_SUCCESS; return ResultCode(ErrorDescription::NoData, ErrorModule::FS, // TODO: verify description ErrorSummary::Canceled, ErrorLevel::Status); @@ -383,13 +348,13 @@ ResultCode CreateDirectoryFromArchive(ArchiveHandle archive_handle, const FileSy ResultCode RenameDirectoryBetweenArchives(ArchiveHandle src_archive_handle, const FileSys::Path& src_path, ArchiveHandle dest_archive_handle, const FileSys::Path& dest_path) { - Archive* src_archive = GetArchive(src_archive_handle); - Archive* dest_archive = GetArchive(dest_archive_handle); + ArchiveBackend* src_archive = GetArchive(src_archive_handle); + ArchiveBackend* dest_archive = GetArchive(dest_archive_handle); if (src_archive == nullptr || dest_archive == nullptr) return ERR_INVALID_HANDLE; if (src_archive == dest_archive) { - if (src_archive->backend->RenameDirectory(src_path, dest_path)) + if (src_archive->RenameDirectory(src_path, dest_path)) return RESULT_SUCCESS; } else { // TODO: Implement renaming across archives @@ -402,31 +367,29 @@ ResultCode RenameDirectoryBetweenArchives(ArchiveHandle src_archive_handle, cons ErrorSummary::NothingHappened, ErrorLevel::Status); } -ResultVal<Kernel::SharedPtr<Kernel::Session>> OpenDirectoryFromArchive(ArchiveHandle archive_handle, +ResultVal<Kernel::SharedPtr<Directory>> OpenDirectoryFromArchive(ArchiveHandle archive_handle, const FileSys::Path& path) { - Archive* archive = GetArchive(archive_handle); + ArchiveBackend* archive = GetArchive(archive_handle); if (archive == nullptr) return ERR_INVALID_HANDLE; - std::unique_ptr<FileSys::DirectoryBackend> backend = archive->backend->OpenDirectory(path); + std::unique_ptr<FileSys::DirectoryBackend> backend = archive->OpenDirectory(path); if (backend == nullptr) { return ResultCode(ErrorDescription::NotFound, ErrorModule::FS, ErrorSummary::NotFound, ErrorLevel::Permanent); } auto directory = Kernel::SharedPtr<Directory>(new Directory(std::move(backend), path)); - return MakeResult<Kernel::SharedPtr<Kernel::Session>>(std::move(directory)); + return MakeResult<Kernel::SharedPtr<Directory>>(std::move(directory)); } -ResultCode FormatSaveData() { - // Do not create the archive again if it already exists - auto archive_itr = id_code_map.find(ArchiveIdCode::SaveData); +ResultCode FormatArchive(ArchiveIdCode id_code, const FileSys::Path& path) { + auto archive_itr = id_code_map.find(id_code); if (archive_itr == id_code_map.end()) { return UnimplementedFunction(ErrorModule::FS); // TODO(Subv): Find the right error } - // Use an empty path, we do not use it when formatting the savedata - return archive_itr->second->backend->Format(FileSys::Path()); + return archive_itr->second->Format(path); } ResultCode CreateExtSaveData(u32 high, u32 low) { @@ -460,32 +423,32 @@ void ArchiveInit() { std::string sdmc_directory = FileUtil::GetUserPath(D_SDMC_IDX); std::string nand_directory = FileUtil::GetUserPath(D_NAND_IDX); - auto sdmc_archive = Common::make_unique<FileSys::Archive_SDMC>(sdmc_directory); - if (sdmc_archive->Initialize()) - CreateArchive(std::move(sdmc_archive), ArchiveIdCode::SDMC); + auto sdmc_factory = Common::make_unique<FileSys::ArchiveFactory_SDMC>(sdmc_directory); + if (sdmc_factory->Initialize()) + RegisterArchiveType(std::move(sdmc_factory), ArchiveIdCode::SDMC); else LOG_ERROR(Service_FS, "Can't instantiate SDMC archive with path %s", sdmc_directory.c_str()); // Create the SaveData archive - auto savedata_archive = Common::make_unique<FileSys::Archive_SaveData>(sdmc_directory); - CreateArchive(std::move(savedata_archive), ArchiveIdCode::SaveData); + auto savedata_factory = Common::make_unique<FileSys::ArchiveFactory_SaveData>(sdmc_directory); + RegisterArchiveType(std::move(savedata_factory), ArchiveIdCode::SaveData); - auto extsavedata_archive = Common::make_unique<FileSys::Archive_ExtSaveData>(sdmc_directory, false); - if (extsavedata_archive->Initialize()) - CreateArchive(std::move(extsavedata_archive), ArchiveIdCode::ExtSaveData); + auto extsavedata_factory = Common::make_unique<FileSys::ArchiveFactory_ExtSaveData>(sdmc_directory, false); + if (extsavedata_factory->Initialize()) + RegisterArchiveType(std::move(extsavedata_factory), ArchiveIdCode::ExtSaveData); else - LOG_ERROR(Service_FS, "Can't instantiate ExtSaveData archive with path %s", extsavedata_archive->GetMountPoint().c_str()); + LOG_ERROR(Service_FS, "Can't instantiate ExtSaveData archive with path %s", extsavedata_factory->GetMountPoint().c_str()); - auto sharedextsavedata_archive = Common::make_unique<FileSys::Archive_ExtSaveData>(nand_directory, true); - if (sharedextsavedata_archive->Initialize()) - CreateArchive(std::move(sharedextsavedata_archive), ArchiveIdCode::SharedExtSaveData); + auto sharedextsavedata_factory = Common::make_unique<FileSys::ArchiveFactory_ExtSaveData>(nand_directory, true); + if (sharedextsavedata_factory->Initialize()) + RegisterArchiveType(std::move(sharedextsavedata_factory), ArchiveIdCode::SharedExtSaveData); else LOG_ERROR(Service_FS, "Can't instantiate SharedExtSaveData archive with path %s", - sharedextsavedata_archive->GetMountPoint().c_str()); + sharedextsavedata_factory->GetMountPoint().c_str()); // Create the SaveDataCheck archive, basically a small variation of the RomFS archive - auto savedatacheck_archive = Common::make_unique<FileSys::Archive_SaveDataCheck>(nand_directory); - CreateArchive(std::move(savedatacheck_archive), ArchiveIdCode::SaveDataCheck); + auto savedatacheck_factory = Common::make_unique<FileSys::ArchiveFactory_SaveDataCheck>(nand_directory); + RegisterArchiveType(std::move(savedatacheck_factory), ArchiveIdCode::SaveDataCheck); } /// Shutdown archives diff --git a/src/core/hle/service/fs/archive.h b/src/core/hle/service/fs/archive.h index ab5ea4da8..c490327d0 100644 --- a/src/core/hle/service/fs/archive.h +++ b/src/core/hle/service/fs/archive.h @@ -8,6 +8,7 @@ #include "core/file_sys/archive_backend.h" #include "core/hle/kernel/kernel.h" +#include "core/hle/kernel/session.h" #include "core/hle/result.h" /// The unique system identifier hash, also known as ID0 @@ -36,6 +37,35 @@ enum class ArchiveIdCode : u32 { typedef u64 ArchiveHandle; +class File : public Kernel::Session { +public: + File(std::unique_ptr<FileSys::FileBackend>&& backend, const FileSys::Path& path) + : path(path), priority(0), backend(std::move(backend)) { + } + + std::string GetName() const override { return "Path: " + path.DebugStr(); } + + FileSys::Path path; ///< Path of the file + u32 priority; ///< Priority of the file. TODO(Subv): Find out what this means + std::unique_ptr<FileSys::FileBackend> backend; ///< File backend interface + + ResultVal<bool> SyncRequest() override; +}; + +class Directory : public Kernel::Session { +public: + Directory(std::unique_ptr<FileSys::DirectoryBackend>&& backend, const FileSys::Path& path) + : path(path), backend(std::move(backend)) { + } + + std::string GetName() const override { return "Directory: " + path.DebugStr(); } + + FileSys::Path path; ///< Path of the directory + std::unique_ptr<FileSys::DirectoryBackend> backend; ///< File backend interface + + ResultVal<bool> SyncRequest() override; +}; + /** * Opens an archive * @param id_code IdCode of the archive to open @@ -51,11 +81,11 @@ ResultVal<ArchiveHandle> OpenArchive(ArchiveIdCode id_code, FileSys::Path& archi ResultCode CloseArchive(ArchiveHandle handle); /** - * Creates an Archive + * Registers an Archive type, instances of which can later be opened using its IdCode. * @param backend File system backend interface to the archive * @param id_code Id code used to access this type of archive */ -ResultCode CreateArchive(std::unique_ptr<FileSys::ArchiveBackend>&& backend, ArchiveIdCode id_code); +ResultCode RegisterArchiveType(std::unique_ptr<FileSys::ArchiveFactory>&& factory, ArchiveIdCode id_code); /** * Open a File from an Archive @@ -64,7 +94,7 @@ ResultCode CreateArchive(std::unique_ptr<FileSys::ArchiveBackend>&& backend, Arc * @param mode Mode under which to open the File * @return The opened File object as a Session */ -ResultVal<Kernel::SharedPtr<Kernel::Session>> OpenFileFromArchive(ArchiveHandle archive_handle, +ResultVal<Kernel::SharedPtr<File>> OpenFileFromArchive(ArchiveHandle archive_handle, const FileSys::Path& path, const FileSys::Mode mode); /** @@ -128,14 +158,17 @@ ResultCode RenameDirectoryBetweenArchives(ArchiveHandle src_archive_handle, cons * @param path Path to the Directory inside of the Archive * @return The opened Directory object as a Session */ -ResultVal<Kernel::SharedPtr<Kernel::Session>> OpenDirectoryFromArchive(ArchiveHandle archive_handle, +ResultVal<Kernel::SharedPtr<Directory>> OpenDirectoryFromArchive(ArchiveHandle archive_handle, const FileSys::Path& path); /** - * Creates a blank SaveData archive. + * Erases the contents of the physical folder that contains the archive + * identified by the specified id code and path + * @param id_code The id of the archive to format + * @param path The path to the archive, if relevant. * @return ResultCode 0 on success or the corresponding code on error */ -ResultCode FormatSaveData(); +ResultCode FormatArchive(ArchiveIdCode id_code, const FileSys::Path& path = FileSys::Path()); /** * Creates a blank SharedExtSaveData archive for the specified extdata ID diff --git a/src/core/hle/service/fs/fs_user.cpp b/src/core/hle/service/fs/fs_user.cpp index 94a3a31c8..71ee4ff55 100644 --- a/src/core/hle/service/fs/fs_user.cpp +++ b/src/core/hle/service/fs/fs_user.cpp @@ -61,7 +61,7 @@ static void OpenFile(Service::Interface* self) { LOG_DEBUG(Service_FS, "path=%s, mode=%d attrs=%u", file_path.DebugStr().c_str(), mode.hex, attributes); - ResultVal<SharedPtr<Session>> file_res = OpenFileFromArchive(archive_handle, file_path, mode); + ResultVal<SharedPtr<File>> file_res = OpenFileFromArchive(archive_handle, file_path, mode); cmd_buff[1] = file_res.Code().raw; if (file_res.Succeeded()) { cmd_buff[3] = Kernel::g_handle_table.Create(*file_res).MoveFrom(); @@ -117,7 +117,7 @@ static void OpenFileDirectly(Service::Interface* self) { } SCOPE_EXIT({ CloseArchive(*archive_handle); }); - ResultVal<SharedPtr<Session>> file_res = OpenFileFromArchive(*archive_handle, file_path, mode); + ResultVal<SharedPtr<File>> file_res = OpenFileFromArchive(*archive_handle, file_path, mode); cmd_buff[1] = file_res.Code().raw; if (file_res.Succeeded()) { cmd_buff[3] = Kernel::g_handle_table.Create(*file_res).MoveFrom(); @@ -337,7 +337,7 @@ static void OpenDirectory(Service::Interface* self) { LOG_DEBUG(Service_FS, "type=%d size=%d data=%s", dirname_type, dirname_size, dir_path.DebugStr().c_str()); - ResultVal<SharedPtr<Session>> dir_res = OpenDirectoryFromArchive(archive_handle, dir_path); + ResultVal<SharedPtr<Directory>> dir_res = OpenDirectoryFromArchive(archive_handle, dir_path); cmd_buff[1] = dir_res.Code().raw; if (dir_res.Succeeded()) { cmd_buff[3] = Kernel::g_handle_table.Create(*dir_res).MoveFrom(); @@ -468,7 +468,7 @@ static void FormatSaveData(Service::Interface* self) { return; } - cmd_buff[1] = FormatSaveData().raw; + cmd_buff[1] = FormatArchive(ArchiveIdCode::SaveData).raw; } /** @@ -484,7 +484,7 @@ static void FormatThisUserSaveData(Service::Interface* self) { // TODO(Subv): Find out what the inputs and outputs of this function are - cmd_buff[1] = FormatSaveData().raw; + cmd_buff[1] = FormatArchive(ArchiveIdCode::SaveData).raw; } static void CreateExtSaveData(Service::Interface* self) { diff --git a/src/core/hle/service/ptm_u.cpp b/src/core/hle/service/ptm_u.cpp index 7b465a348..7c8d9ce8c 100644 --- a/src/core/hle/service/ptm_u.cpp +++ b/src/core/hle/service/ptm_u.cpp @@ -4,8 +4,9 @@ #include "common/log.h" #include "common/make_unique.h" -#include "core/file_sys/archive_extsavedata.h" + #include "core/hle/hle.h" +#include "core/hle/service/fs/archive.h" #include "core/hle/service/ptm_u.h" //////////////////////////////////////////////////////////////////////////////////////////////////// @@ -28,7 +29,6 @@ struct GameCoin { u8 day; }; static const GameCoin default_game_coin = { 0x4F00, 42, 0, 0, 0, 2014, 12, 29 }; -static std::unique_ptr<FileSys::Archive_ExtSaveData> ptm_shared_extsavedata; static const std::vector<u8> ptm_shared_extdata_id = {0, 0, 0, 0, 0x0B, 0, 0, 0xF0, 0, 0, 0, 0}; /// Charge levels used by PTM functions @@ -138,31 +138,28 @@ const Interface::FunctionInfo FunctionTable[] = { Interface::Interface() { Register(FunctionTable); - // Create the SharedExtSaveData archive 0xF000000B and the gamecoin.dat file - // TODO(Subv): In the future we should use the FS service to query this archive - std::string nand_directory = FileUtil::GetUserPath(D_NAND_IDX); - ptm_shared_extsavedata = Common::make_unique<FileSys::Archive_ExtSaveData>(nand_directory, true); - if (!ptm_shared_extsavedata->Initialize()) { - LOG_CRITICAL(Service_PTM, "Could not initialize SharedExtSaveData archive for the PTM:U service"); - return; - } + + // Open the SharedExtSaveData archive 0xF000000B and the gamecoin.dat file FileSys::Path archive_path(ptm_shared_extdata_id); - ResultCode result = ptm_shared_extsavedata->Open(archive_path); + auto archive_result = Service::FS::OpenArchive(Service::FS::ArchiveIdCode::SharedExtSaveData, archive_path); // If the archive didn't exist, create the files inside - if (result.description == ErrorDescription::FS_NotFormatted) { - // Format the archive to clear the directories - ptm_shared_extsavedata->Format(archive_path); + if (archive_result.Code().description == ErrorDescription::FS_NotFormatted) { + // Format the archive to create the directories + Service::FS::FormatArchive(Service::FS::ArchiveIdCode::SharedExtSaveData, archive_path); // Open it again to get a valid archive now that the folder exists - ptm_shared_extsavedata->Open(archive_path); + archive_result = Service::FS::OpenArchive(Service::FS::ArchiveIdCode::SharedExtSaveData, archive_path); + _assert_msg_(Service_PTM, archive_result.Succeeded(), "Could not open the PTM SharedExtSaveData archive!"); + FileSys::Path gamecoin_path("gamecoin.dat"); FileSys::Mode open_mode = {}; open_mode.write_flag = 1; open_mode.create_flag = 1; // Open the file and write the default gamecoin information - auto gamecoin = ptm_shared_extsavedata->OpenFile(gamecoin_path, open_mode); - if (gamecoin != nullptr) { - gamecoin->Write(0, sizeof(GameCoin), 1, reinterpret_cast<const u8*>(&default_game_coin)); - gamecoin->Close(); + auto gamecoin_result = Service::FS::OpenFileFromArchive(*archive_result, gamecoin_path, open_mode); + if (gamecoin_result.Succeeded()) { + auto gamecoin = gamecoin_result.MoveFrom(); + gamecoin->backend->Write(0, sizeof(GameCoin), 1, reinterpret_cast<const u8*>(&default_game_coin)); + gamecoin->backend->Close(); } } } |