From 24e7b465be75a4bd431cb855d81cb1f69186c249 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?L=C3=A9o=20Lam?= Date: Sat, 19 Aug 2017 11:21:00 +0200 Subject: [PATCH 1/2] IOS: Rename MemoryValues to VersionInfo --- Source/Core/Core/CMakeLists.txt | 2 +- Source/Core/Core/Core.vcxproj | 4 ++-- Source/Core/Core/Core.vcxproj.filters | 8 ++++---- Source/Core/Core/IOS/IOS.cpp | 2 +- .../Core/Core/IOS/{MemoryValues.cpp => VersionInfo.cpp} | 2 +- Source/Core/Core/IOS/{MemoryValues.h => VersionInfo.h} | 0 6 files changed, 9 insertions(+), 9 deletions(-) rename Source/Core/Core/IOS/{MemoryValues.cpp => VersionInfo.cpp} (99%) rename Source/Core/Core/IOS/{MemoryValues.h => VersionInfo.h} (100%) diff --git a/Source/Core/Core/CMakeLists.txt b/Source/Core/Core/CMakeLists.txt index 96bbe1d15c95..2ac4c204c111 100644 --- a/Source/Core/Core/CMakeLists.txt +++ b/Source/Core/Core/CMakeLists.txt @@ -155,8 +155,8 @@ set(SRCS IOS/DeviceStub.cpp IOS/IOS.cpp IOS/IOSC.cpp - IOS/MemoryValues.cpp IOS/MIOS.cpp + IOS/VersionInfo.cpp IOS/DI/DI.cpp IOS/ES/ES.cpp IOS/ES/Formats.cpp diff --git a/Source/Core/Core/Core.vcxproj b/Source/Core/Core/Core.vcxproj index 5e275711dea2..10e0e019b9e9 100644 --- a/Source/Core/Core/Core.vcxproj +++ b/Source/Core/Core/Core.vcxproj @@ -185,8 +185,8 @@ - + @@ -442,8 +442,8 @@ - + diff --git a/Source/Core/Core/Core.vcxproj.filters b/Source/Core/Core/Core.vcxproj.filters index 167fcec00770..c9f2ea8deb3a 100644 --- a/Source/Core/Core/Core.vcxproj.filters +++ b/Source/Core/Core/Core.vcxproj.filters @@ -769,10 +769,10 @@ IOS - + IOS - + IOS @@ -1511,10 +1511,10 @@ IOS - + IOS - + IOS diff --git a/Source/Core/Core/IOS/IOS.cpp b/Source/Core/Core/IOS/IOS.cpp index 3d372c7688b6..464093018c7a 100644 --- a/Source/Core/Core/IOS/IOS.cpp +++ b/Source/Core/Core/IOS/IOS.cpp @@ -32,7 +32,6 @@ #include "Core/IOS/FS/FS.h" #include "Core/IOS/FS/FileIO.h" #include "Core/IOS/MIOS.h" -#include "Core/IOS/MemoryValues.h" #include "Core/IOS/Network/IP/Top.h" #include "Core/IOS/Network/KD/NetKDRequest.h" #include "Core/IOS/Network/KD/NetKDTime.h" @@ -50,6 +49,7 @@ #include "Core/IOS/USB/USB_HID/HIDv5.h" #include "Core/IOS/USB/USB_KBD.h" #include "Core/IOS/USB/USB_VEN/VEN.h" +#include "Core/IOS/VersionInfo.h" #include "Core/IOS/WFS/WFSI.h" #include "Core/IOS/WFS/WFSSRV.h" #include "Core/PowerPC/PowerPC.h" diff --git a/Source/Core/Core/IOS/MemoryValues.cpp b/Source/Core/Core/IOS/VersionInfo.cpp similarity index 99% rename from Source/Core/Core/IOS/MemoryValues.cpp rename to Source/Core/Core/IOS/VersionInfo.cpp index ec05088df584..8008998be74e 100644 --- a/Source/Core/Core/IOS/MemoryValues.cpp +++ b/Source/Core/Core/IOS/VersionInfo.cpp @@ -2,7 +2,7 @@ // Licensed under GPLv2+ // Refer to the license.txt file included. -#include "Core/IOS/MemoryValues.h" +#include "Core/IOS/VersionInfo.h" #include diff --git a/Source/Core/Core/IOS/MemoryValues.h b/Source/Core/Core/IOS/VersionInfo.h similarity index 100% rename from Source/Core/Core/IOS/MemoryValues.h rename to Source/Core/Core/IOS/VersionInfo.h From e4ea4da78215918371ad85a798d20de4d81e7f01 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?L=C3=A9o=20Lam?= Date: Sat, 19 Aug 2017 15:55:10 +0200 Subject: [PATCH 2/2] IOS: Check for available features when adding devices Prevents resource managers that shouldn't be visible from being exposed to titles. This adds a new function to get features for an IOS version, and also moves the version checks from the modules themselves to VersionInfo. This hopefully documents some of the differences between IOS better and should be slightly cleaner than having random version checks. --- Source/Core/Core/IOS/IOS.cpp | 68 +++++++++++++++++----- Source/Core/Core/IOS/SDIO/SDIOSlot0.cpp | 23 +------- Source/Core/Core/IOS/USB/OH0/OH0.cpp | 4 +- Source/Core/Core/IOS/USB/OH0/OH0Device.cpp | 4 -- Source/Core/Core/IOS/USB/USB_VEN/VEN.cpp | 8 --- Source/Core/Core/IOS/USB/USB_VEN/VEN.h | 1 - Source/Core/Core/IOS/VersionInfo.cpp | 39 +++++++++++++ Source/Core/Core/IOS/VersionInfo.h | 46 +++++++++++++++ 8 files changed, 142 insertions(+), 51 deletions(-) diff --git a/Source/Core/Core/IOS/IOS.cpp b/Source/Core/Core/IOS/IOS.cpp index 464093018c7a..d782c3f5b636 100644 --- a/Source/Core/Core/IOS/IOS.cpp +++ b/Source/Core/Core/IOS/IOS.cpp @@ -345,32 +345,69 @@ void Kernel::AddStaticDevices() { std::lock_guard lock(m_device_map_mutex); + const Feature features = GetFeatures(GetVersion()); + + // OH1 (Bluetooth) + AddDevice(std::make_unique(*this, "/dev/usb/oh1")); if (!SConfig::GetInstance().m_bt_passthrough_enabled) AddDevice(std::make_unique(*this, "/dev/usb/oh1/57e/305")); else AddDevice(std::make_unique(*this, "/dev/usb/oh1/57e/305")); + // Other core modules AddDevice(std::make_unique(*this, "/dev/stm/immediate")); AddDevice(std::make_unique(*this, "/dev/stm/eventhook")); AddDevice(std::make_unique(*this, "/dev/di")); - AddDevice(std::make_unique(*this, "/dev/net/kd/request")); - AddDevice(std::make_unique(*this, "/dev/net/kd/time")); - AddDevice(std::make_unique(*this, "/dev/net/ncd/manage")); - AddDevice(std::make_unique(*this, "/dev/net/wd/command")); - AddDevice(std::make_unique(*this, "/dev/net/ip/top")); - AddDevice(std::make_unique(*this, "/dev/net/ssl")); - AddDevice(std::make_unique(*this, "/dev/usb/kbd")); AddDevice(std::make_unique(*this, "/dev/sdio/slot0")); AddDevice(std::make_unique(*this, "/dev/sdio/slot1")); - if (GetVersion() == 59) + + // Network modules + if (HasFeature(features, Feature::KD)) + { + AddDevice(std::make_unique(*this, "/dev/net/kd/request")); + AddDevice(std::make_unique(*this, "/dev/net/kd/time")); + } + if (HasFeature(features, Feature::NCD)) + { + AddDevice(std::make_unique(*this, "/dev/net/ncd/manage")); + } + if (HasFeature(features, Feature::WiFi)) + { + AddDevice(std::make_unique(*this, "/dev/net/wd/command")); + } + if (HasFeature(features, Feature::SO)) + { + AddDevice(std::make_unique(*this, "/dev/net/ip/top")); + } + if (HasFeature(features, Feature::SSL)) + { + AddDevice(std::make_unique(*this, "/dev/net/ssl")); + } + + // USB modules + // OH0 is unconditionally added because this device path is registered in all cases. + AddDevice(std::make_unique(*this, "/dev/usb/oh0")); + if (HasFeature(features, Feature::NewUSB)) + { AddDevice(std::make_unique(*this, "/dev/usb/hid")); + AddDevice(std::make_unique(*this, "/dev/usb/ven")); + + // TODO(IOS): register /dev/usb/usb, /dev/usb/msc, /dev/usb/hub and /dev/usb/ehc + // as stubs that return IPC_EACCES. + } else - AddDevice(std::make_unique(*this, "/dev/usb/hid")); - AddDevice(std::make_unique(*this, "/dev/usb/oh0")); - AddDevice(std::make_unique(*this, "/dev/usb/oh1")); - AddDevice(std::make_unique(*this, "/dev/usb/ven")); - AddDevice(std::make_unique(*this, "/dev/usb/wfssrv")); - AddDevice(std::make_unique(*this, "/dev/wfsi")); + { + if (HasFeature(features, Feature::USB_HIDv4)) + AddDevice(std::make_unique(*this, "/dev/usb/hid")); + if (HasFeature(features, Feature::USB_KBD)) + AddDevice(std::make_unique(*this, "/dev/usb/kbd")); + } + + if (HasFeature(features, Feature::WFS)) + { + AddDevice(std::make_unique(*this, "/dev/usb/wfssrv")); + AddDevice(std::make_unique(*this, "/dev/wfsi")); + } } s32 Kernel::GetFreeDeviceID() @@ -411,7 +448,8 @@ s32 Kernel::OpenDevice(OpenRequest& request) request.fd = new_fd; std::shared_ptr device; - if (request.path.find("/dev/usb/oh0/") == 0 && !GetDeviceByName(request.path)) + if (request.path.find("/dev/usb/oh0/") == 0 && !GetDeviceByName(request.path) && + !HasFeature(GetVersion(), Feature::NewUSB)) { device = std::make_shared(*this, request.path); } diff --git a/Source/Core/Core/IOS/SDIO/SDIOSlot0.cpp b/Source/Core/Core/IOS/SDIO/SDIOSlot0.cpp index a832c66b3879..362d6284dcce 100644 --- a/Source/Core/Core/IOS/SDIO/SDIOSlot0.cpp +++ b/Source/Core/Core/IOS/SDIO/SDIOSlot0.cpp @@ -18,6 +18,7 @@ #include "Core/ConfigManager.h" #include "Core/HW/Memmap.h" #include "Core/IOS/IOS.h" +#include "Core/IOS/VersionInfo.h" namespace IOS { @@ -25,28 +26,8 @@ namespace HLE { namespace Device { -constexpr bool SupportsSDHC(u32 ios_version) -{ - switch (ios_version) - { - // Known versions to support SDHC - case 48: - case 56: - case 57: - case 58: - case 59: - case 60: - case 61: - case 70: - case 80: - return true; - default: - return false; - }; -} - SDIOSlot0::SDIOSlot0(Kernel& ios, const std::string& device_name) - : Device(ios, device_name), m_sdhc_supported(SupportsSDHC(ios.GetVersion())) + : Device(ios, device_name), m_sdhc_supported(HasFeature(ios.GetVersion(), Feature::SDv2)) { } diff --git a/Source/Core/Core/IOS/USB/OH0/OH0.cpp b/Source/Core/Core/IOS/USB/OH0/OH0.cpp index 85760299bd18..3b574bcc5c73 100644 --- a/Source/Core/Core/IOS/USB/OH0/OH0.cpp +++ b/Source/Core/Core/IOS/USB/OH0/OH0.cpp @@ -18,6 +18,7 @@ #include "Core/HW/Memmap.h" #include "Core/IOS/USB/Common.h" #include "Core/IOS/USB/USBV0.h" +#include "Core/IOS/VersionInfo.h" namespace IOS { @@ -36,8 +37,7 @@ OH0::~OH0() ReturnCode OH0::Open(const OpenRequest& request) { - const u32 ios_major_version = m_ios.GetVersion(); - if (ios_major_version == 57 || ios_major_version == 58 || ios_major_version == 59) + if (HasFeature(m_ios.GetVersion(), Feature::NewUSB)) return IPC_EACCES; return USBHost::Open(request); } diff --git a/Source/Core/Core/IOS/USB/OH0/OH0Device.cpp b/Source/Core/Core/IOS/USB/OH0/OH0Device.cpp index ab1cafc25ba0..0b8c56d0eae1 100644 --- a/Source/Core/Core/IOS/USB/OH0/OH0Device.cpp +++ b/Source/Core/Core/IOS/USB/OH0/OH0Device.cpp @@ -57,10 +57,6 @@ void OH0Device::DoState(PointerWrap& p) ReturnCode OH0Device::Open(const OpenRequest& request) { - const u32 ios_major_version = m_ios.GetVersion(); - if (ios_major_version == 57 || ios_major_version == 58 || ios_major_version == 59) - return IPC_ENOENT; - if (m_vid == 0 && m_pid == 0) return IPC_ENOENT; diff --git a/Source/Core/Core/IOS/USB/USB_VEN/VEN.cpp b/Source/Core/Core/IOS/USB/USB_VEN/VEN.cpp index 955710f1768a..e2a327a7b785 100644 --- a/Source/Core/Core/IOS/USB/USB_VEN/VEN.cpp +++ b/Source/Core/Core/IOS/USB/USB_VEN/VEN.cpp @@ -35,14 +35,6 @@ USB_VEN::~USB_VEN() StopThreads(); } -ReturnCode USB_VEN::Open(const OpenRequest& request) -{ - const u32 ios_major_version = m_ios.GetVersion(); - if (ios_major_version != 57 && ios_major_version != 58 && ios_major_version != 59) - return IPC_ENOENT; - return USBHost::Open(request); -} - IPCCommandResult USB_VEN::IOCtl(const IOCtlRequest& request) { request.Log(GetDeviceName(), LogTypes::IOS_USB); diff --git a/Source/Core/Core/IOS/USB/USB_VEN/VEN.h b/Source/Core/Core/IOS/USB/USB_VEN/VEN.h index ed8d71a8d7bd..dc128d01f96f 100644 --- a/Source/Core/Core/IOS/USB/USB_VEN/VEN.h +++ b/Source/Core/Core/IOS/USB/USB_VEN/VEN.h @@ -31,7 +31,6 @@ class USB_VEN final : public USBHost USB_VEN(Kernel& ios, const std::string& device_name); ~USB_VEN() override; - ReturnCode Open(const OpenRequest& request) override; IPCCommandResult IOCtl(const IOCtlRequest& request) override; IPCCommandResult IOCtlV(const IOCtlVRequest& request) override; diff --git a/Source/Core/Core/IOS/VersionInfo.cpp b/Source/Core/Core/IOS/VersionInfo.cpp index 8008998be74e..38e4eb003ece 100644 --- a/Source/Core/Core/IOS/VersionInfo.cpp +++ b/Source/Core/Core/IOS/VersionInfo.cpp @@ -335,5 +335,44 @@ const std::array& GetMemoryValues() { return ios_memory_values; } + +Feature GetFeatures(u32 version) +{ + // Common features that are present in most versions. + Feature features = Feature::Core | Feature::SDIO | Feature::SO | Feature::Ethernet; + + // IOS4 is a tiny IOS that was presumably used during manufacturing. It lacks network support. + if (version != 4) + features |= Feature::KD | Feature::SSL | Feature::NCD | Feature::WiFi; + + if (version == 48 || (version >= 56 && version <= 62) || version == 70 || version == 80) + features |= Feature::SDv2; + + if (version == 57 || version == 58 || version == 59) + features |= Feature::NewUSB; + if (version == 58 || version == 59) + features |= Feature::EHCI; + if (version == 59) + features |= Feature::WFS; + + // No IOS earlier than IOS30 has USB_KBD. Any IOS with the new USB modules lacks this module. + // TODO(IOS): it is currently unknown which other versions don't have it. + if (version >= 30 && !HasFeature(features, Feature::NewUSB)) + features |= Feature::USB_KBD; + + // Just like KBD, USB_HIDv4 is not present on any IOS with the new USB modules + // (since it's been replaced with USB_HIDv5 there). + // Additionally, it appears that HIDv4 and KBD are never both present. + // TODO(IOS): figure out which versions have HIDv4. For now we just include both KBD and HIDv4. + if (!HasFeature(features, Feature::NewUSB)) + features |= Feature::USB_HIDv4; + + return features; +} + +bool HasFeature(u32 major_version, Feature feature) +{ + return HasFeature(GetFeatures(major_version), feature); +} } } diff --git a/Source/Core/Core/IOS/VersionInfo.h b/Source/Core/Core/IOS/VersionInfo.h index d04dedd9c5b1..1b64b8b2aa94 100644 --- a/Source/Core/Core/IOS/VersionInfo.h +++ b/Source/Core/Core/IOS/VersionInfo.h @@ -37,5 +37,51 @@ struct MemoryValues }; const std::array& GetMemoryValues(); + +enum class Feature +{ + // Kernel, ES, FS, STM, DI, OH0, OH1 + Core = 1 << 0, + // SDIO + SDIO = 1 << 1, + // Network (base support: SO, Ethernet; KD, SSL, NCD, Wi-Fi) + SO = 1 << 2, + Ethernet = 1 << 3, + KD = 1 << 4, + SSL = 1 << 5, + NCD = 1 << 6, + WiFi = 1 << 7, + // KBD + USB_KBD = 1 << 8, + // USB_HID v4 + USB_HIDv4 = 1 << 9, + // SDv2 support + SDv2 = 1 << 10, + // New USB modules (USB, USB_VEN, USB_HUB, USB_MSC, OHCI0, USB_HIDv5) + NewUSB = 1 << 11, + // EHCI + EHCI = 1 << 12, + // WFS (WFSSRV, WFSI, USB_SHARED) + WFS = 1 << 13, +}; + +constexpr Feature operator|(Feature lhs, Feature rhs) +{ + return static_cast(static_cast(lhs) | static_cast(rhs)); +} + +constexpr Feature& operator|=(Feature& lhs, Feature rhs) +{ + lhs = lhs | rhs; + return lhs; +} + +constexpr bool HasFeature(Feature features, Feature feature) +{ + return (static_cast(features) & static_cast(feature)) != 0; +} + +bool HasFeature(u32 major_version, Feature feature); +Feature GetFeatures(u32 major_version); } }