From 657470830fbd9cc14cef628e8299811acafd08ec Mon Sep 17 00:00:00 2001 From: Michael Scire Date: Fri, 21 Aug 2020 02:37:06 -0700 Subject: [PATCH] loader: support MapRegion capability as an atmosphere extension (normally kips-only) --- .../vapours/results/loader_results.hpp | 1 + .../loader/source/ldr_capabilities.cpp | 31 +++++++++++++++++++ 2 files changed, 32 insertions(+) diff --git a/libraries/libvapours/include/vapours/results/loader_results.hpp b/libraries/libvapours/include/vapours/results/loader_results.hpp index 1ffa7ae13..8f21b6ed8 100644 --- a/libraries/libvapours/include/vapours/results/loader_results.hpp +++ b/libraries/libvapours/include/vapours/results/loader_results.hpp @@ -54,6 +54,7 @@ namespace ams::ldr { R_DEFINE_ERROR_RESULT(InvalidCapabilitySyscallMask, 104); R_DEFINE_ERROR_RESULT(InvalidCapabilityMapRange, 106); R_DEFINE_ERROR_RESULT(InvalidCapabilityMapPage, 107); + R_DEFINE_ERROR_RESULT(InvalidCapabilityMapRegion, 110); R_DEFINE_ERROR_RESULT(InvalidCapabilityInterruptPair, 111); R_DEFINE_ERROR_RESULT(InvalidCapabilityApplicationType, 113); R_DEFINE_ERROR_RESULT(InvalidCapabilityKernelVersion, 114); diff --git a/stratosphere/loader/source/ldr_capabilities.cpp b/stratosphere/loader/source/ldr_capabilities.cpp index 6c170863c..2766fe26c 100644 --- a/stratosphere/loader/source/ldr_capabilities.cpp +++ b/stratosphere/loader/source/ldr_capabilities.cpp @@ -26,6 +26,7 @@ namespace ams::ldr::caps { SyscallMask = 4, MapRange = 6, MapPage = 7, + MapRegion = 10, InterruptPair = 11, ApplicationType = 13, KernelVersion = 14, @@ -181,6 +182,35 @@ namespace ams::ldr::caps { } ); + enum class MemoryRegionType : u32 { + None = 0, + KernelTraceBuffer = 1, + OnMemoryBootImage = 2, + DTB = 3, + }; + + DEFINE_CAPABILITY_CLASS(MapRegion, + DEFINE_CAPABILITY_FIELD(Region0, IdBits, 6, MemoryRegionType); + DEFINE_CAPABILITY_FIELD(ReadOnly0, Region0, 1, bool); + DEFINE_CAPABILITY_FIELD(Region1, ReadOnly0, 6, MemoryRegionType); + DEFINE_CAPABILITY_FIELD(ReadOnly1, Region1, 1, bool); + DEFINE_CAPABILITY_FIELD(Region2, ReadOnly1, 6, MemoryRegionType); + DEFINE_CAPABILITY_FIELD(ReadOnly2, Region2, 1, bool); + + bool IsValid(const util::BitPack32 *kac, size_t kac_count) const { + for (size_t i = 0; i < kac_count; i++) { + if (GetCapabilityId(kac[i]) == Id) { + const auto restriction = Decode(kac[i]); + + if (this->GetValue() == restriction.GetValue()) { + return true; + } + } + } + return false; + } + ); + DEFINE_CAPABILITY_CLASS(InterruptPair, DEFINE_CAPABILITY_FIELD(InterruptId0, IdBits, 10); DEFINE_CAPABILITY_FIELD(InterruptId1, InterruptId0, 10); @@ -304,6 +334,7 @@ namespace ams::ldr::caps { VALIDATE_CASE(KernelFlags); VALIDATE_CASE(SyscallMask); VALIDATE_CASE(MapPage); + VALIDATE_CASE(MapRegion); VALIDATE_CASE(InterruptPair); VALIDATE_CASE(ApplicationType); VALIDATE_CASE(KernelVersion);