Result<Metadata> HostFileSystem::GetMetadata(Uid, Gid, const std::string& path) { Metadata metadata; metadata.uid = 0; metadata.gid = 0x3031; // this is also known as makercd, 01 (0x3031) for nintendo and 08 // (0x3038) for MH3 etc if (!IsValidWiiPath(path)) return ResultCode::Invalid; std::string file_name = BuildFilename(path); metadata.modes = {Mode::ReadWrite, Mode::ReadWrite, Mode::ReadWrite}; metadata.attribute = 0x00; // no attributes // Hack: if the path that is being accessed is within an installed title directory, get the // UID/GID from the installed title TMD. Kernel* ios = GetIOS(); u64 title_id; if (ios && IsTitlePath(file_name, Common::FROM_SESSION_ROOT, &title_id)) { IOS::ES::TMDReader tmd = ios->GetES()->FindInstalledTMD(title_id); if (tmd.IsValid()) metadata.gid = tmd.GetGroupId(); } const File::FileInfo info{file_name}; metadata.is_file = info.IsFile(); metadata.size = info.GetSize(); if (!info.Exists()) return ResultCode::NotFound; return metadata; }
void MainMenuBar::RefreshWiiSystemMenuLabel() const { auto* const item = FindItem(IDM_LOAD_WII_MENU); if (Core::IsRunning()) { item->Enable(false); for (const int idm : {IDM_PERFORM_ONLINE_UPDATE_CURRENT, IDM_PERFORM_ONLINE_UPDATE_EUR, IDM_PERFORM_ONLINE_UPDATE_JPN, IDM_PERFORM_ONLINE_UPDATE_KOR, IDM_PERFORM_ONLINE_UPDATE_USA}) { FindItem(idm)->Enable(false); } return; } IOS::HLE::Kernel ios; const IOS::ES::TMDReader sys_menu_tmd = ios.GetES()->FindInstalledTMD(Titles::SYSTEM_MENU); if (sys_menu_tmd.IsValid()) { const u16 version_number = sys_menu_tmd.GetTitleVersion(); const wxString version_string = StrToWxStr(DiscIO::GetSysMenuVersionString(version_number)); item->Enable(); item->SetItemLabel(wxString::Format(_("Load Wii System Menu %s"), version_string)); EnableUpdateMenu(UpdateMenuMode::CurrentRegionOnly); } else { item->Enable(false); item->SetItemLabel(_("Load Wii System Menu")); EnableUpdateMenu(UpdateMenuMode::SpecificRegionsOnly); } }
IPCCommandResult ES::GetStoredContents(const IOCtlVRequest& request) { if (!request.HasNumberOfValidVectors(2, 1) || request.in_vectors[0].size != sizeof(u64)) return GetDefaultReply(ES_EINVAL); const u64 title_id = Memory::Read_U64(request.in_vectors[0].address); const IOS::ES::TMDReader tmd = FindInstalledTMD(title_id); if (!tmd.IsValid()) return GetDefaultReply(FS_ENOENT); return GetStoredContents(tmd, request); }
// Used by the GetStoredContents ioctlvs. This assumes that the first output vector // is used for the content count (u32). IPCCommandResult ES::GetStoredContentsCount(const IOS::ES::TMDReader& tmd, const IOCtlVRequest& request) { if (request.io_vectors[0].size != sizeof(u32) || !tmd.IsValid()) return GetDefaultReply(ES_EINVAL); const u16 num_contents = static_cast<u16>(GetStoredContentsFromTMD(tmd).size()); Memory::Write_U32(num_contents, request.io_vectors[0].address); INFO_LOG(IOS_ES, "GetStoredContentsCount (0x%x): %u content(s) for %016" PRIx64, request.request, num_contents, tmd.GetTitleId()); return GetDefaultReply(IPC_SUCCESS); }
void InfoPanel::LoadISODetails() { m_internal_name->SetValue(StrToWxStr(m_opened_iso->GetInternalName())); m_game_id->SetValue(StrToWxStr(m_opened_iso->GetGameID())); m_country->SetValue(GetCountryName(m_opened_iso->GetCountry())); m_maker_id->SetValue("0x" + StrToWxStr(m_opened_iso->GetMakerID())); m_revision->SetValue(OptionalToString(m_opened_iso->GetRevision())); m_date->SetValue(StrToWxStr(m_opened_iso->GetApploaderDate())); if (m_ios_version) { const IOS::ES::TMDReader tmd = m_opened_iso->GetTMD(m_opened_iso->GetGamePartition()); if (tmd.IsValid()) m_ios_version->SetValue(StringFromFormat("IOS%u", static_cast<u32>(tmd.GetIOSId()))); } }
IPCCommandResult ES::GetStoredTMDSize(const IOCtlVRequest& request) { if (!request.HasNumberOfValidVectors(1, 1)) return GetDefaultReply(ES_EINVAL); const u64 title_id = Memory::Read_U64(request.in_vectors[0].address); const IOS::ES::TMDReader tmd = FindInstalledTMD(title_id); if (!tmd.IsValid()) return GetDefaultReply(FS_ENOENT); const u32 tmd_size = static_cast<u32>(tmd.GetBytes().size()); Memory::Write_U32(tmd_size, request.io_vectors[0].address); INFO_LOG(IOS_ES, "GetStoredTMDSize: %u bytes for %016" PRIx64, tmd_size, title_id); return GetDefaultReply(IPC_SUCCESS); }
// Used by the GetStoredContents ioctlvs. This assumes that the second input vector is used // for the content count and the output vector is used to store a list of content IDs (u32s). IPCCommandResult ES::GetStoredContents(const IOS::ES::TMDReader& tmd, const IOCtlVRequest& request) { if (!tmd.IsValid()) return GetDefaultReply(ES_EINVAL); if (request.in_vectors[1].size != sizeof(u32) || request.io_vectors[0].size != Memory::Read_U32(request.in_vectors[1].address) * sizeof(u32)) { return GetDefaultReply(ES_EINVAL); } const auto contents = GetStoredContentsFromTMD(tmd); const u32 max_content_count = Memory::Read_U32(request.in_vectors[1].address); for (u32 i = 0; i < std::min(static_cast<u32>(contents.size()), max_content_count); ++i) Memory::Write_U32(contents[i].id, request.io_vectors[0].address + i * sizeof(u32)); return GetDefaultReply(IPC_SUCCESS); }
IPCCommandResult ES::GetStoredTMD(const IOCtlVRequest& request) { if (!request.HasNumberOfValidVectors(2, 1)) return GetDefaultReply(ES_EINVAL); const u64 title_id = Memory::Read_U64(request.in_vectors[0].address); const IOS::ES::TMDReader tmd = FindInstalledTMD(title_id); if (!tmd.IsValid()) return GetDefaultReply(FS_ENOENT); // TODO: actually use this param in when writing to the outbuffer :/ const u32 MaxCount = Memory::Read_U32(request.in_vectors[1].address); const std::vector<u8>& raw_tmd = tmd.GetBytes(); if (raw_tmd.size() != request.io_vectors[0].size) return GetDefaultReply(ES_EINVAL); Memory::CopyToEmu(request.io_vectors[0].address, raw_tmd.data(), raw_tmd.size()); INFO_LOG(IOS_ES, "GetStoredTMD: title %016" PRIx64 " (buffer size: %u)", title_id, MaxCount); return GetDefaultReply(IPC_SUCCESS); }
IPCCommandResult ES::GetTMDStoredContents(const IOCtlVRequest& request) { if (!request.HasNumberOfValidVectors(2, 1)) return GetDefaultReply(ES_EINVAL); std::vector<u8> tmd_bytes(request.in_vectors[0].size); Memory::CopyFromEmu(tmd_bytes.data(), request.in_vectors[0].address, tmd_bytes.size()); const IOS::ES::TMDReader tmd{std::move(tmd_bytes)}; if (!tmd.IsValid()) return GetDefaultReply(ES_EINVAL); std::vector<u8> cert_store; ReturnCode ret = ReadCertStore(&cert_store); if (ret != IPC_SUCCESS) return GetDefaultReply(ret); ret = VerifyContainer(VerifyContainerType::TMD, VerifyMode::UpdateCertStore, tmd, cert_store); if (ret != IPC_SUCCESS) return GetDefaultReply(ret); return GetStoredContents(tmd, request); }