diff --git a/libraries/libstratosphere/include/stratosphere/spl/impl/spl_api_impl.hpp b/libraries/libstratosphere/include/stratosphere/spl/impl/spl_api_impl.hpp index b64d84140..db2354329 100644 --- a/libraries/libstratosphere/include/stratosphere/spl/impl/spl_api_impl.hpp +++ b/libraries/libstratosphere/include/stratosphere/spl/impl/spl_api_impl.hpp @@ -51,7 +51,7 @@ namespace ams::spl::impl { Result AllocateAesKeySlot(s32 *out_keyslot); Result DeallocateAesKeySlot(s32 keyslot); - Result TestAesKeySlot(s32 *out_index, s32 keyslot); + Result TestAesKeySlot(s32 *out_index, bool *out_virtual, s32 keyslot); os::SystemEvent *GetAesKeySlotAvailableEvent(); diff --git a/libraries/libstratosphere/source/spl/impl/spl_api_impl.cpp b/libraries/libstratosphere/source/spl/impl/spl_api_impl.cpp index ed1fe8833..a4183c389 100644 --- a/libraries/libstratosphere/source/spl/impl/spl_api_impl.cpp +++ b/libraries/libstratosphere/source/spl/impl/spl_api_impl.cpp @@ -729,9 +729,10 @@ namespace ams::spl::impl { return ResultSuccess(); } - Result TestAesKeySlot(s32 *out_index, s32 keyslot) { + Result TestAesKeySlot(s32 *out_index, bool *out_virtual, s32 keyslot) { if (g_is_physical_keyslot_allowed && IsPhysicalAesKeySlot(keyslot)) { - *out_index = keyslot; + *out_index = keyslot; + *out_virtual = false; return ResultSuccess(); } @@ -740,7 +741,8 @@ namespace ams::spl::impl { const s32 index = GetVirtualAesKeySlotIndex(keyslot); R_UNLESS(g_is_aes_keyslot_allocated[index], spl::ResultInvalidKeySlot()); - *out_index = index; + *out_index = index; + *out_virtual = true; return ResultSuccess(); } diff --git a/stratosphere/spl/source/spl_secure_monitor_manager.cpp b/stratosphere/spl/source/spl_secure_monitor_manager.cpp index 15d077c95..daeb0808e 100644 --- a/stratosphere/spl/source/spl_secure_monitor_manager.cpp +++ b/stratosphere/spl/source/spl_secure_monitor_manager.cpp @@ -131,11 +131,17 @@ namespace ams::spl { } Result SecureMonitorManager::AllocateAesKeySlot(s32 *out_keyslot, const void *owner) { + /* Allocate a new virtual keyslot. */ s32 keyslot; R_TRY(impl::AllocateAesKeySlot(std::addressof(keyslot))); + /* Get the keyslot's index. */ s32 index; - R_ABORT_UNLESS(impl::TestAesKeySlot(std::addressof(index), keyslot)); + bool virt; + R_ABORT_UNLESS(impl::TestAesKeySlot(std::addressof(index), std::addressof(virt), keyslot)); + + /* All allocated keyslots must be virtual. */ + AMS_ABORT_UNLESS(virt); m_aes_keyslot_owners[index] = owner; *out_keyslot = keyslot; @@ -174,10 +180,11 @@ namespace ams::spl { Result SecureMonitorManager::TestAesKeySlot(s32 *out_index, s32 keyslot, const void *owner) { /* Validate the keyslot (and get the index). */ s32 index; - R_TRY(impl::TestAesKeySlot(std::addressof(index), keyslot)); + bool virt; + R_TRY(impl::TestAesKeySlot(std::addressof(index), std::addressof(virt), keyslot)); - /* Check that the keyslot is owned by the request maker. */ - R_UNLESS(m_aes_keyslot_owners[index] == owner, spl::ResultInvalidKeySlot()); + /* Check that the keyslot is physical (for legacy compat) or owned by the request maker. */ + R_UNLESS(!virt || m_aes_keyslot_owners[index] == owner, spl::ResultInvalidKeySlot()); /* Set output index. */ if (out_index != nullptr) {