From 8e50d6002bd12dde7e4ba4fd3da1b53864c4058c Mon Sep 17 00:00:00 2001 From: bunnei Date: Sat, 20 Jan 2018 21:32:36 -0500 Subject: fsp_srv: Various improvements to IStorage:Read implementation. --- src/core/hle/service/filesystem/fsp_srv.cpp | 92 +++++++++++++++-------------- 1 file changed, 49 insertions(+), 43 deletions(-) (limited to 'src/core/hle/service/filesystem/fsp_srv.cpp') diff --git a/src/core/hle/service/filesystem/fsp_srv.cpp b/src/core/hle/service/filesystem/fsp_srv.cpp index 47a97f0fd..ef1915e5a 100644 --- a/src/core/hle/service/filesystem/fsp_srv.cpp +++ b/src/core/hle/service/filesystem/fsp_srv.cpp @@ -20,9 +20,8 @@ public: IStorage(std::unique_ptr&& backend) : ServiceFramework("IStorage"), backend(std::move(backend)) { static const FunctionInfo functions[] = { - {0, &IStorage::Read, "Read"}, {1, &IStorage::Write, "Write"}, - {2, &IStorage::Flush, "Flush"}, {3, &IStorage::SetSize, "SetSize"}, - {4, &IStorage::GetSize, "GetSize"}, + {0, &IStorage::Read, "Read"}, {1, nullptr, "Write"}, {2, nullptr, "Flush"}, + {3, nullptr, "SetSize"}, {4, nullptr, "GetSize"}, }; RegisterHandlers(functions); } @@ -32,49 +31,40 @@ private: void Read(Kernel::HLERequestContext& ctx) { IPC::RequestParser rp{ctx}; - u64 offset = rp.Pop(); - u64 length = rp.Pop(); + const s64 offset = rp.Pop(); + const s64 length = rp.Pop(); + const auto& descriptor = ctx.BufferDescriptorB()[0]; - LOG_DEBUG(Service, "called, offset=0x%llx, length=0x%llx", offset, length); + LOG_DEBUG(Service_FS, "called, offset=0x%llx, length=0x%llx", offset, length); - auto descriptor = ctx.BufferDescriptorB()[0]; - std::vector output(length); + // Error checking + ASSERT_MSG(length == descriptor.Size(), "unexpected size difference"); + if (length < 0) { + IPC::RequestBuilder rb{ctx, 2}; + rb.Push(ResultCode(ErrorModule::FS, ErrorDescription::InvalidLength)); + return; + } + if (offset < 0) { + IPC::RequestBuilder rb{ctx, 2}; + rb.Push(ResultCode(ErrorModule::FS, ErrorDescription::InvalidOffset)); + return; + } + // Read the data from the Storage backend + std::vector output(length); ResultVal res = backend->Read(offset, length, output.data()); if (res.Failed()) { IPC::RequestBuilder rb{ctx, 2}; rb.Push(res.Code()); + return; } + // Write the data to memory Memory::WriteBlock(descriptor.Address(), output.data(), descriptor.Size()); IPC::RequestBuilder rb{ctx, 2}; rb.Push(RESULT_SUCCESS); } - - void Write(Kernel::HLERequestContext& ctx) { - IPC::RequestBuilder rb{ctx, 2}; - rb.Push(RESULT_SUCCESS); - LOG_WARNING(Service, "(STUBBED) called"); - } - - void Flush(Kernel::HLERequestContext& ctx) { - IPC::RequestBuilder rb{ctx, 2}; - rb.Push(RESULT_SUCCESS); - LOG_WARNING(Service, "(STUBBED) called"); - } - - void SetSize(Kernel::HLERequestContext& ctx) { - IPC::RequestBuilder rb{ctx, 2}; - rb.Push(RESULT_SUCCESS); - LOG_WARNING(Service, "(STUBBED) called"); - } - - void GetSize(Kernel::HLERequestContext& ctx) { - IPC::RequestBuilder rb{ctx, 2}; - rb.Push(RESULT_SUCCESS); - LOG_WARNING(Service, "(STUBBED) called"); - } }; FSP_SRV::FSP_SRV() : ServiceFramework("fsp-srv") { @@ -87,46 +77,62 @@ FSP_SRV::FSP_SRV() : ServiceFramework("fsp-srv") { RegisterHandlers(functions); } +void FSP_SRV::TryLoadRomFS() { + if (romfs) { + return; + } + FileSys::Path unused; + auto res = OpenFileSystem(Type::RomFS, unused); + if (res.Succeeded()) { + romfs = std::move(res.Unwrap()); + } +} + void FSP_SRV::Initalize(Kernel::HLERequestContext& ctx) { + LOG_WARNING(Service_FS, "(STUBBED) called"); + IPC::RequestBuilder rb{ctx, 2}; rb.Push(RESULT_SUCCESS); - LOG_WARNING(Service, "(STUBBED) called"); } void FSP_SRV::GetGlobalAccessLogMode(Kernel::HLERequestContext& ctx) { + LOG_WARNING(Service_FS, "(STUBBED) called"); + IPC::RequestBuilder rb{ctx, 4}; rb.Push(RESULT_SUCCESS); rb.Push(5); - LOG_WARNING(Service, "(STUBBED) called"); } void FSP_SRV::OpenDataStorageByCurrentProcess(Kernel::HLERequestContext& ctx) { - FileSys::Path path; - auto filesystem = OpenFileSystem(Type::RomFS, path); - if (filesystem.Failed()) { + LOG_DEBUG(Service_FS, "called"); + + TryLoadRomFS(); + if (!romfs) { + // TODO (bunnei): Find the right error code to use here + LOG_CRITICAL(Service_FS, "no file system interface available!"); IPC::RequestBuilder rb{ctx, 2}; - rb.Push(filesystem.Code()); + rb.Push(ResultCode(-1)); return; } - auto storage = filesystem.Unwrap()->OpenFile({}, {}); + // Attempt to open a StorageBackend interface to the RomFS + auto storage = romfs->OpenFile({}, {}); if (storage.Failed()) { + LOG_CRITICAL(Service_FS, "no storage interface available!"); IPC::RequestBuilder rb{ctx, 2}; rb.Push(storage.Code()); return; } - // TODO: What if already opened? - IPC::RequestBuilder rb{ctx, 2, 0, 0, 1}; rb.Push(RESULT_SUCCESS); rb.PushIpcInterface(std::move(storage.Unwrap())); - LOG_WARNING(Service, "(STUBBED) called"); } void FSP_SRV::OpenRomStorage(Kernel::HLERequestContext& ctx) { + LOG_WARNING(Service_FS, "(STUBBED) called, using OpenDataStorageByCurrentProcess"); OpenDataStorageByCurrentProcess(ctx); } -} // namespace Filesystem +} // namespace FileSystem } // namespace Service -- cgit v1.2.3