mirror of
				https://github.com/PabloMK7/citra.git
				synced 2025-10-31 05:40:04 +00:00 
			
		
		
		
	HLE/FS: Change the error code returned when an ExtSaveData archive is not found.
This allows Fire Emblem to boot again.
This commit is contained in:
		
							parent
							
								
									3aa42627a3
								
							
						
					
					
						commit
						f707026ac5
					
				
					 5 changed files with 45 additions and 33 deletions
				
			
		|  | @ -11,6 +11,7 @@ | |||
| 
 | ||||
| #include "common/bit_field.h" | ||||
| #include "common/common_types.h" | ||||
| #include "common/swap.h" | ||||
| 
 | ||||
| #include "core/hle/result.h" | ||||
| 
 | ||||
|  | @ -63,9 +64,9 @@ private: | |||
| }; | ||||
| 
 | ||||
| struct ArchiveFormatInfo { | ||||
|     u32 total_size; ///< The pre-defined size of the archive, as specified in the Create or Format call
 | ||||
|     u32 number_directories; ///< The pre-defined number of directories in the archive, as specified in the Create or Format call
 | ||||
|     u32 number_files; ///< The pre-defined number of files in the archive, as specified in the Create or Format call
 | ||||
|     u32_le total_size; ///< The pre-defined size of the archive, as specified in the Create or Format call
 | ||||
|     u32_le number_directories; ///< The pre-defined number of directories in the archive, as specified in the Create or Format call
 | ||||
|     u32_le number_files; ///< The pre-defined number of files in the archive, as specified in the Create or Format call
 | ||||
|     u8 duplicate_data; ///< Whether the archive should duplicate the data, as specified in the Create or Format call
 | ||||
| }; | ||||
| static_assert(std::is_pod<ArchiveFormatInfo>::value, "ArchiveFormatInfo is not POD"); | ||||
|  |  | |||
|  | @ -58,7 +58,7 @@ Path ConstructExtDataBinaryPath(u32 media_type, u32 high, u32 low) { | |||
| } | ||||
| 
 | ||||
| ArchiveFactory_ExtSaveData::ArchiveFactory_ExtSaveData(const std::string& mount_location, bool shared) | ||||
|         : mount_point(GetExtDataContainerPath(mount_location, shared)) { | ||||
|         : shared(shared), mount_point(GetExtDataContainerPath(mount_location, shared)) { | ||||
|     LOG_INFO(Service_FS, "Directory %s set as base for ExtSaveData.", mount_point.c_str()); | ||||
| } | ||||
| 
 | ||||
|  | @ -74,9 +74,15 @@ bool ArchiveFactory_ExtSaveData::Initialize() { | |||
| ResultVal<std::unique_ptr<ArchiveBackend>> ArchiveFactory_ExtSaveData::Open(const Path& path) { | ||||
|     std::string fullpath = GetExtSaveDataPath(mount_point, path) + "user/"; | ||||
|     if (!FileUtil::Exists(fullpath)) { | ||||
|         // TODO(Subv): Check error code, this one is probably wrong
 | ||||
|         return ResultCode(ErrorDescription::FS_NotFormatted, ErrorModule::FS, | ||||
|             ErrorSummary::InvalidState, ErrorLevel::Status); | ||||
|         // TODO(Subv): Verify the archive behavior of SharedExtSaveData compared to ExtSaveData.
 | ||||
|         // ExtSaveData seems to return FS_NotFound (120) when the archive doesn't exist.
 | ||||
|         if (!shared) { | ||||
|             return ResultCode(ErrorDescription::FS_NotFound, ErrorModule::FS, | ||||
|                               ErrorSummary::InvalidState, ErrorLevel::Status); | ||||
|         } else { | ||||
|             return ResultCode(ErrorDescription::FS_NotFormatted, ErrorModule::FS, | ||||
|                               ErrorSummary::InvalidState, ErrorLevel::Status); | ||||
|         } | ||||
|     } | ||||
|     auto archive = Common::make_unique<DiskArchive>(fullpath); | ||||
|     return MakeResult<std::unique_ptr<ArchiveBackend>>(std::move(archive)); | ||||
|  | @ -93,33 +99,33 @@ ResultCode ArchiveFactory_ExtSaveData::Format(const Path& path, const FileSys::A | |||
|     std::string metadata_path = GetExtSaveDataPath(mount_point, path) + "metadata"; | ||||
|     FileUtil::IOFile file(metadata_path, "wb"); | ||||
| 
 | ||||
|     if (file.IsOpen()) { | ||||
|         file.WriteBytes(&format_info, sizeof(format_info)); | ||||
|         return RESULT_SUCCESS; | ||||
|     if (!file.IsOpen()) { | ||||
|         // TODO(Subv): Find the correct error code
 | ||||
|         return ResultCode(-1); | ||||
|     } | ||||
| 
 | ||||
|     // TODO(Subv): Find the correct error code
 | ||||
|     return ResultCode(-1); | ||||
|     file.WriteBytes(&format_info, sizeof(format_info)); | ||||
|     return RESULT_SUCCESS; | ||||
| } | ||||
| 
 | ||||
| ResultVal<ArchiveFormatInfo> ArchiveFactory_ExtSaveData::GetFormatInfo(const Path& path) const { | ||||
|     std::string metadata_path = GetExtSaveDataPath(mount_point, path) + "metadata"; | ||||
|     FileUtil::IOFile file(metadata_path, "rb"); | ||||
| 
 | ||||
|     if (file.IsOpen()) { | ||||
|         ArchiveFormatInfo info; | ||||
|         file.ReadBytes(&info, sizeof(info)); | ||||
|         return MakeResult<ArchiveFormatInfo>(info); | ||||
|     if (!file.IsOpen()) { | ||||
|         LOG_ERROR(Service_FS, "Could not open metadata information for archive"); | ||||
|         // TODO(Subv): Verify error code
 | ||||
|         return ResultCode(ErrorDescription::FS_NotFormatted, ErrorModule::FS, ErrorSummary::InvalidState, ErrorLevel::Status); | ||||
|     } | ||||
| 
 | ||||
|     LOG_ERROR(Service_FS, "Could not open metadata information for archive"); | ||||
|     // TODO(Subv): Verify error code
 | ||||
|     return ResultCode(ErrorDescription::FS_NotFormatted, ErrorModule::FS, ErrorSummary::InvalidState, ErrorLevel::Status); | ||||
|     ArchiveFormatInfo info = {}; | ||||
|     file.ReadBytes(&info, sizeof(info)); | ||||
|     return MakeResult<ArchiveFormatInfo>(info); | ||||
| } | ||||
| 
 | ||||
| void ArchiveFactory_ExtSaveData::WriteIcon(const Path& path, const u8* icon_data, u32 icon_size) { | ||||
| void ArchiveFactory_ExtSaveData::WriteIcon(const Path& path, const u8* icon_data, size_t icon_size) { | ||||
|     std::string game_path = FileSys::GetExtSaveDataPath(GetMountPoint(), path); | ||||
|     FileUtil::IOFile icon_file(game_path + "icon", "wb+"); | ||||
|     FileUtil::IOFile icon_file(game_path + "icon", "wb"); | ||||
|     icon_file.WriteBytes(icon_data, icon_size); | ||||
| } | ||||
| 
 | ||||
|  |  | |||
|  | @ -42,7 +42,7 @@ public: | |||
|      * @param icon_data Binary data of the icon | ||||
|      * @param icon_size Size of the icon data | ||||
|      */ | ||||
|     void WriteIcon(const Path& path, const u8* icon_data, u32 icon_size); | ||||
|     void WriteIcon(const Path& path, const u8* icon_data, size_t icon_size); | ||||
| 
 | ||||
| private: | ||||
|     /**
 | ||||
|  | @ -51,6 +51,7 @@ private: | |||
|      * See GetExtSaveDataPath for the code that extracts this data from an archive path. | ||||
|      */ | ||||
|     std::string mount_point; | ||||
|     bool shared; ///< Whether this archive represents an ExtSaveData archive or a SharedExtSaveData archive
 | ||||
| }; | ||||
| 
 | ||||
| /**
 | ||||
|  |  | |||
|  | @ -77,15 +77,15 @@ ResultVal<ArchiveFormatInfo> ArchiveFactory_SaveData::GetFormatInfo(const Path& | |||
|     std::string metadata_path = GetSaveDataMetadataPath(mount_point, Kernel::g_current_process->codeset->program_id); | ||||
|     FileUtil::IOFile file(metadata_path, "rb"); | ||||
| 
 | ||||
|     if (file.IsOpen()) { | ||||
|         ArchiveFormatInfo info; | ||||
|         file.ReadBytes(&info, sizeof(info)); | ||||
|         return MakeResult<ArchiveFormatInfo>(info); | ||||
|     if (!file.IsOpen()) { | ||||
|         LOG_ERROR(Service_FS, "Could not open metadata information for archive"); | ||||
|         // TODO(Subv): Verify error code
 | ||||
|         return ResultCode(ErrorDescription::FS_NotFormatted, ErrorModule::FS, ErrorSummary::InvalidState, ErrorLevel::Status); | ||||
|     } | ||||
| 
 | ||||
|     LOG_ERROR(Service_FS, "Could not open metadata information for archive"); | ||||
|     // TODO(Subv): Verify error code
 | ||||
|     return ResultCode(ErrorDescription::FS_NotFormatted, ErrorModule::FS, ErrorSummary::InvalidState, ErrorLevel::Status); | ||||
|     ArchiveFormatInfo info = {}; | ||||
|     file.ReadBytes(&info, sizeof(info)); | ||||
|     return MakeResult<ArchiveFormatInfo>(info); | ||||
| } | ||||
| 
 | ||||
| } // namespace FileSys
 | ||||
|  |  | |||
|  | @ -103,14 +103,18 @@ ResultVal<bool> File::SyncRequest() { | |||
|             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); | ||||
|             if (offset + length > backend->GetSize()) | ||||
|                 LOG_ERROR(Service_FS, "Reading from out of bounds offset=0x%llX length=0x%08X file_size=0x%llX", offset, length, backend->GetSize()); | ||||
| 
 | ||||
|             if (offset + length > backend->GetSize()) { | ||||
|                 LOG_ERROR(Service_FS, "Reading from out of bounds offset=0x%llX length=0x%08X file_size=0x%llX", | ||||
|                           offset, length, backend->GetSize()); | ||||
|             } | ||||
| 
 | ||||
|             ResultVal<size_t> read = backend->Read(offset, length, Memory::GetPointer(address)); | ||||
|             if (read.Failed()) { | ||||
|                 cmd_buff[1] = read.Code().raw; | ||||
|                 return read.Code(); | ||||
|             } | ||||
|             cmd_buff[2] = static_cast<u32>(read.MoveFrom()); | ||||
|             cmd_buff[2] = static_cast<u32>(*read); | ||||
|             break; | ||||
|         } | ||||
| 
 | ||||
|  | @ -129,7 +133,7 @@ ResultVal<bool> File::SyncRequest() { | |||
|                 cmd_buff[1] = written.Code().raw; | ||||
|                 return written.Code(); | ||||
|             } | ||||
|             cmd_buff[2] = static_cast<u32>(written.MoveFrom()); | ||||
|             cmd_buff[2] = static_cast<u32>(*written); | ||||
|             break; | ||||
|         } | ||||
| 
 | ||||
|  |  | |||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue