From 87426b29ffa4329c8a47ac8ee661b0074b3d5ee1 Mon Sep 17 00:00:00 2001
From: Weiyi Wang <wwylele@gmail.com>
Date: Sat, 13 Oct 2018 17:08:37 -0400
Subject: [PATCH] kernel: pass ref to shared memory

---
 src/core/hle/applets/erreula.cpp       |  3 +-
 src/core/hle/applets/mii_selector.cpp  |  3 +-
 src/core/hle/applets/mint.cpp          |  3 +-
 src/core/hle/applets/swkbd.cpp         |  3 +-
 src/core/hle/kernel/kernel.h           | 55 ++++++++++++++++++++++++++
 src/core/hle/kernel/process.h          |  6 ---
 src/core/hle/kernel/shared_memory.cpp  | 23 ++++++-----
 src/core/hle/kernel/shared_memory.h    | 51 ++----------------------
 src/core/hle/kernel/svc.cpp            |  6 +--
 src/core/hle/service/apt/apt.cpp       |  6 +--
 src/core/hle/service/csnd/csnd_snd.cpp |  6 +--
 src/core/hle/service/gsp/gsp_gpu.cpp   |  6 +--
 src/core/hle/service/hid/hid.cpp       |  6 +--
 src/core/hle/service/ir/ir_rst.cpp     |  6 +--
 14 files changed, 95 insertions(+), 88 deletions(-)

diff --git a/src/core/hle/applets/erreula.cpp b/src/core/hle/applets/erreula.cpp
index a8135a2ae..7b8cf1d02 100644
--- a/src/core/hle/applets/erreula.cpp
+++ b/src/core/hle/applets/erreula.cpp
@@ -3,6 +3,7 @@
 // Refer to the license.txt file included.
 
 #include "common/string_util.h"
+#include "core/core.h"
 #include "core/hle/applets/erreula.h"
 #include "core/hle/service/apt/apt.h"
 
@@ -30,7 +31,7 @@ ResultCode ErrEula::ReceiveParameter(const Service::APT::MessageParameter& param
     // Allocate a heap block of the required size for this applet.
     heap_memory = std::make_shared<std::vector<u8>>(capture_info.size);
     // Create a SharedMemory that directly points to this heap block.
-    framebuffer_memory = Kernel::SharedMemory::CreateForApplet(
+    framebuffer_memory = Core::System::GetInstance().Kernel().CreateSharedMemoryForApplet(
         heap_memory, 0, capture_info.size, MemoryPermission::ReadWrite, MemoryPermission::ReadWrite,
         "ErrEula Memory");
 
diff --git a/src/core/hle/applets/mii_selector.cpp b/src/core/hle/applets/mii_selector.cpp
index cfe25b11d..dd57f0efd 100644
--- a/src/core/hle/applets/mii_selector.cpp
+++ b/src/core/hle/applets/mii_selector.cpp
@@ -7,6 +7,7 @@
 #include "common/assert.h"
 #include "common/logging/log.h"
 #include "common/string_util.h"
+#include "core/core.h"
 #include "core/hle/applets/mii_selector.h"
 #include "core/hle/kernel/kernel.h"
 #include "core/hle/kernel/shared_memory.h"
@@ -37,7 +38,7 @@ ResultCode MiiSelector::ReceiveParameter(const Service::APT::MessageParameter& p
     // Allocate a heap block of the required size for this applet.
     heap_memory = std::make_shared<std::vector<u8>>(capture_info.size);
     // Create a SharedMemory that directly points to this heap block.
-    framebuffer_memory = Kernel::SharedMemory::CreateForApplet(
+    framebuffer_memory = Core::System::GetInstance().Kernel().CreateSharedMemoryForApplet(
         heap_memory, 0, capture_info.size, MemoryPermission::ReadWrite, MemoryPermission::ReadWrite,
         "MiiSelector Memory");
 
diff --git a/src/core/hle/applets/mint.cpp b/src/core/hle/applets/mint.cpp
index d71cd7001..ee70ba615 100644
--- a/src/core/hle/applets/mint.cpp
+++ b/src/core/hle/applets/mint.cpp
@@ -3,6 +3,7 @@
 // Refer to the license.txt file included.
 
 #include "common/string_util.h"
+#include "core/core.h"
 #include "core/hle/applets/mint.h"
 #include "core/hle/service/apt/apt.h"
 
@@ -30,7 +31,7 @@ ResultCode Mint::ReceiveParameter(const Service::APT::MessageParameter& paramete
     // Allocate a heap block of the required size for this applet.
     heap_memory = std::make_shared<std::vector<u8>>(capture_info.size);
     // Create a SharedMemory that directly points to this heap block.
-    framebuffer_memory = Kernel::SharedMemory::CreateForApplet(
+    framebuffer_memory = Core::System::GetInstance().Kernel().CreateSharedMemoryForApplet(
         heap_memory, 0, capture_info.size, MemoryPermission::ReadWrite, MemoryPermission::ReadWrite,
         "Mint Memory");
 
diff --git a/src/core/hle/applets/swkbd.cpp b/src/core/hle/applets/swkbd.cpp
index d13050002..cd8a9f57a 100644
--- a/src/core/hle/applets/swkbd.cpp
+++ b/src/core/hle/applets/swkbd.cpp
@@ -8,6 +8,7 @@
 #include "common/assert.h"
 #include "common/logging/log.h"
 #include "common/string_util.h"
+#include "core/core.h"
 #include "core/hle/applets/swkbd.h"
 #include "core/hle/kernel/kernel.h"
 #include "core/hle/kernel/shared_memory.h"
@@ -41,7 +42,7 @@ ResultCode SoftwareKeyboard::ReceiveParameter(Service::APT::MessageParameter con
     // Allocate a heap block of the required size for this applet.
     heap_memory = std::make_shared<std::vector<u8>>(capture_info.size);
     // Create a SharedMemory that directly points to this heap block.
-    framebuffer_memory = Kernel::SharedMemory::CreateForApplet(
+    framebuffer_memory = Core::System::GetInstance().Kernel().CreateSharedMemoryForApplet(
         heap_memory, 0, capture_info.size, MemoryPermission::ReadWrite, MemoryPermission::ReadWrite,
         "SoftwareKeyboard Memory");
 
diff --git a/src/core/hle/kernel/kernel.h b/src/core/hle/kernel/kernel.h
index 84a33d8e6..4d0390408 100644
--- a/src/core/hle/kernel/kernel.h
+++ b/src/core/hle/kernel/kernel.h
@@ -25,6 +25,7 @@ class ServerPort;
 class ClientSession;
 class ServerSession;
 class ResourceLimitList;
+class SharedMemory;
 
 enum class ResetType {
     OneShot,
@@ -32,6 +33,25 @@ enum class ResetType {
     Pulse,
 };
 
+/// Permissions for mapped shared memory blocks
+enum class MemoryPermission : u32 {
+    None = 0,
+    Read = (1u << 0),
+    Write = (1u << 1),
+    ReadWrite = (Read | Write),
+    Execute = (1u << 2),
+    ReadExecute = (Read | Execute),
+    WriteExecute = (Write | Execute),
+    ReadWriteExecute = (Read | Write | Execute),
+    DontCare = (1u << 28)
+};
+
+enum class MemoryRegion : u16 {
+    APPLICATION = 1,
+    SYSTEM = 2,
+    BASE = 3,
+};
+
 template <typename T>
 using SharedPtr = boost::intrusive_ptr<T>;
 
@@ -122,6 +142,41 @@ public:
     ResourceLimitList& ResourceLimit();
     const ResourceLimitList& ResourceLimit() const;
 
+    /**
+     * Creates a shared memory object.
+     * @param owner_process Process that created this shared memory object.
+     * @param size Size of the memory block. Must be page-aligned.
+     * @param permissions Permission restrictions applied to the process which created the block.
+     * @param other_permissions Permission restrictions applied to other processes mapping the
+     * block.
+     * @param address The address from which to map the Shared Memory.
+     * @param region If the address is 0, the shared memory will be allocated in this region of the
+     * linear heap.
+     * @param name Optional object name, used for debugging purposes.
+     */
+    SharedPtr<SharedMemory> CreateSharedMemory(SharedPtr<Process> owner_process, u32 size,
+                                               MemoryPermission permissions,
+                                               MemoryPermission other_permissions,
+                                               VAddr address = 0,
+                                               MemoryRegion region = MemoryRegion::BASE,
+                                               std::string name = "Unknown");
+
+    /**
+     * Creates a shared memory object from a block of memory managed by an HLE applet.
+     * @param heap_block Heap block of the HLE applet.
+     * @param offset The offset into the heap block that the SharedMemory will map.
+     * @param size Size of the memory block. Must be page-aligned.
+     * @param permissions Permission restrictions applied to the process which created the block.
+     * @param other_permissions Permission restrictions applied to other processes mapping the
+     * block.
+     * @param name Optional object name, used for debugging purposes.
+     */
+    SharedPtr<SharedMemory> CreateSharedMemoryForApplet(std::shared_ptr<std::vector<u8>> heap_block,
+                                                        u32 offset, u32 size,
+                                                        MemoryPermission permissions,
+                                                        MemoryPermission other_permissions,
+                                                        std::string name = "Unknown Applet");
+
 private:
     std::unique_ptr<ResourceLimitList> resource_limits;
 };
diff --git a/src/core/hle/kernel/process.h b/src/core/hle/kernel/process.h
index edf4928ff..a141dff4c 100644
--- a/src/core/hle/kernel/process.h
+++ b/src/core/hle/kernel/process.h
@@ -26,12 +26,6 @@ struct AddressMapping {
     bool unk_flag;
 };
 
-enum class MemoryRegion : u16 {
-    APPLICATION = 1,
-    SYSTEM = 2,
-    BASE = 3,
-};
-
 union ProcessFlags {
     u16 raw;
 
diff --git a/src/core/hle/kernel/shared_memory.cpp b/src/core/hle/kernel/shared_memory.cpp
index f5b9dad2c..14a206c59 100644
--- a/src/core/hle/kernel/shared_memory.cpp
+++ b/src/core/hle/kernel/shared_memory.cpp
@@ -11,14 +11,15 @@
 
 namespace Kernel {
 
-SharedMemory::SharedMemory() {}
+SharedMemory::SharedMemory(KernelSystem& system) {}
 SharedMemory::~SharedMemory() {}
 
-SharedPtr<SharedMemory> SharedMemory::Create(SharedPtr<Process> owner_process, u32 size,
-                                             MemoryPermission permissions,
-                                             MemoryPermission other_permissions, VAddr address,
-                                             MemoryRegion region, std::string name) {
-    SharedPtr<SharedMemory> shared_memory(new SharedMemory);
+SharedPtr<SharedMemory> KernelSystem::CreateSharedMemory(SharedPtr<Process> owner_process, u32 size,
+                                                         MemoryPermission permissions,
+                                                         MemoryPermission other_permissions,
+                                                         VAddr address, MemoryRegion region,
+                                                         std::string name) {
+    SharedPtr<SharedMemory> shared_memory(new SharedMemory(*this));
 
     shared_memory->owner_process = owner_process;
     shared_memory->name = std::move(name);
@@ -74,12 +75,10 @@ SharedPtr<SharedMemory> SharedMemory::Create(SharedPtr<Process> owner_process, u
     return shared_memory;
 }
 
-SharedPtr<SharedMemory> SharedMemory::CreateForApplet(std::shared_ptr<std::vector<u8>> heap_block,
-                                                      u32 offset, u32 size,
-                                                      MemoryPermission permissions,
-                                                      MemoryPermission other_permissions,
-                                                      std::string name) {
-    SharedPtr<SharedMemory> shared_memory(new SharedMemory);
+SharedPtr<SharedMemory> KernelSystem::CreateSharedMemoryForApplet(
+    std::shared_ptr<std::vector<u8>> heap_block, u32 offset, u32 size, MemoryPermission permissions,
+    MemoryPermission other_permissions, std::string name) {
+    SharedPtr<SharedMemory> shared_memory(new SharedMemory(*this));
 
     shared_memory->owner_process = nullptr;
     shared_memory->name = std::move(name);
diff --git a/src/core/hle/kernel/shared_memory.h b/src/core/hle/kernel/shared_memory.h
index 5ccd81572..d5d862927 100644
--- a/src/core/hle/kernel/shared_memory.h
+++ b/src/core/hle/kernel/shared_memory.h
@@ -12,55 +12,8 @@
 
 namespace Kernel {
 
-/// Permissions for mapped shared memory blocks
-enum class MemoryPermission : u32 {
-    None = 0,
-    Read = (1u << 0),
-    Write = (1u << 1),
-    ReadWrite = (Read | Write),
-    Execute = (1u << 2),
-    ReadExecute = (Read | Execute),
-    WriteExecute = (Write | Execute),
-    ReadWriteExecute = (Read | Write | Execute),
-    DontCare = (1u << 28)
-};
-
 class SharedMemory final : public Object {
 public:
-    /**
-     * Creates a shared memory object.
-     * @param owner_process Process that created this shared memory object.
-     * @param size Size of the memory block. Must be page-aligned.
-     * @param permissions Permission restrictions applied to the process which created the block.
-     * @param other_permissions Permission restrictions applied to other processes mapping the
-     * block.
-     * @param address The address from which to map the Shared Memory.
-     * @param region If the address is 0, the shared memory will be allocated in this region of the
-     * linear heap.
-     * @param name Optional object name, used for debugging purposes.
-     */
-    static SharedPtr<SharedMemory> Create(SharedPtr<Process> owner_process, u32 size,
-                                          MemoryPermission permissions,
-                                          MemoryPermission other_permissions, VAddr address = 0,
-                                          MemoryRegion region = MemoryRegion::BASE,
-                                          std::string name = "Unknown");
-
-    /**
-     * Creates a shared memory object from a block of memory managed by an HLE applet.
-     * @param heap_block Heap block of the HLE applet.
-     * @param offset The offset into the heap block that the SharedMemory will map.
-     * @param size Size of the memory block. Must be page-aligned.
-     * @param permissions Permission restrictions applied to the process which created the block.
-     * @param other_permissions Permission restrictions applied to other processes mapping the
-     * block.
-     * @param name Optional object name, used for debugging purposes.
-     */
-    static SharedPtr<SharedMemory> CreateForApplet(std::shared_ptr<std::vector<u8>> heap_block,
-                                                   u32 offset, u32 size,
-                                                   MemoryPermission permissions,
-                                                   MemoryPermission other_permissions,
-                                                   std::string name = "Unknown Applet");
-
     std::string GetTypeName() const override {
         return "SharedMemory";
     }
@@ -125,8 +78,10 @@ public:
     std::string name;
 
 private:
-    SharedMemory();
+    explicit SharedMemory(KernelSystem& kernel);
     ~SharedMemory() override;
+
+    friend class KernelSystem;
 };
 
 } // namespace Kernel
diff --git a/src/core/hle/kernel/svc.cpp b/src/core/hle/kernel/svc.cpp
index 632d2e539..3e292bd3b 100644
--- a/src/core/hle/kernel/svc.cpp
+++ b/src/core/hle/kernel/svc.cpp
@@ -1105,9 +1105,9 @@ static ResultCode CreateMemoryBlock(Handle* out_handle, u32 addr, u32 size, u32
     if (addr == 0 && g_current_process->flags.shared_device_mem)
         region = g_current_process->flags.memory_region;
 
-    shared_memory =
-        SharedMemory::Create(g_current_process, size, static_cast<MemoryPermission>(my_permission),
-                             static_cast<MemoryPermission>(other_permission), addr, region);
+    shared_memory = Core::System::GetInstance().Kernel().CreateSharedMemory(
+        g_current_process, size, static_cast<MemoryPermission>(my_permission),
+        static_cast<MemoryPermission>(other_permission), addr, region);
     CASCADE_RESULT(*out_handle, g_handle_table.Create(std::move(shared_memory)));
 
     LOG_WARNING(Kernel_SVC, "called addr=0x{:08X}", addr);
diff --git a/src/core/hle/service/apt/apt.cpp b/src/core/hle/service/apt/apt.cpp
index 752e65c2c..13c278158 100644
--- a/src/core/hle/service/apt/apt.cpp
+++ b/src/core/hle/service/apt/apt.cpp
@@ -855,9 +855,9 @@ Module::Module(Core::System& system) : system(system) {
 
     using Kernel::MemoryPermission;
     shared_font_mem =
-        Kernel::SharedMemory::Create(nullptr, 0x332000, // 3272 KB
-                                     MemoryPermission::ReadWrite, MemoryPermission::Read, 0,
-                                     Kernel::MemoryRegion::SYSTEM, "APT:SharedFont");
+        system.Kernel().CreateSharedMemory(nullptr, 0x332000, // 3272 KB
+                                           MemoryPermission::ReadWrite, MemoryPermission::Read, 0,
+                                           Kernel::MemoryRegion::SYSTEM, "APT:SharedFont");
 
     lock = system.Kernel().CreateMutex(false, "APT_U:Lock");
 }
diff --git a/src/core/hle/service/csnd/csnd_snd.cpp b/src/core/hle/service/csnd/csnd_snd.cpp
index 8fc4f11f4..ec4f55c0d 100644
--- a/src/core/hle/service/csnd/csnd_snd.cpp
+++ b/src/core/hle/service/csnd/csnd_snd.cpp
@@ -20,9 +20,9 @@ void CSND_SND::Initialize(Kernel::HLERequestContext& ctx) {
 
     using Kernel::MemoryPermission;
     mutex = system.Kernel().CreateMutex(false, "CSND:mutex");
-    shared_memory = Kernel::SharedMemory::Create(nullptr, size, MemoryPermission::ReadWrite,
-                                                 MemoryPermission::ReadWrite, 0,
-                                                 Kernel::MemoryRegion::BASE, "CSND:SharedMemory");
+    shared_memory = system.Kernel().CreateSharedMemory(
+        nullptr, size, MemoryPermission::ReadWrite, MemoryPermission::ReadWrite, 0,
+        Kernel::MemoryRegion::BASE, "CSND:SharedMemory");
 
     IPC::RequestBuilder rb = rp.MakeBuilder(1, 3);
     rb.Push(RESULT_SUCCESS);
diff --git a/src/core/hle/service/gsp/gsp_gpu.cpp b/src/core/hle/service/gsp/gsp_gpu.cpp
index be2a7ca64..a6b4826e2 100644
--- a/src/core/hle/service/gsp/gsp_gpu.cpp
+++ b/src/core/hle/service/gsp/gsp_gpu.cpp
@@ -786,9 +786,9 @@ GSP_GPU::GSP_GPU(Core::System& system) : ServiceFramework("gsp::Gpu", 2), system
     RegisterHandlers(functions);
 
     using Kernel::MemoryPermission;
-    shared_memory = Kernel::SharedMemory::Create(nullptr, 0x1000, MemoryPermission::ReadWrite,
-                                                 MemoryPermission::ReadWrite, 0,
-                                                 Kernel::MemoryRegion::BASE, "GSP:SharedMemory");
+    shared_memory = system.Kernel().CreateSharedMemory(
+        nullptr, 0x1000, MemoryPermission::ReadWrite, MemoryPermission::ReadWrite, 0,
+        Kernel::MemoryRegion::BASE, "GSP:SharedMemory");
 
     first_initialization = true;
 };
diff --git a/src/core/hle/service/hid/hid.cpp b/src/core/hle/service/hid/hid.cpp
index 322a0b193..205d7860e 100644
--- a/src/core/hle/service/hid/hid.cpp
+++ b/src/core/hle/service/hid/hid.cpp
@@ -359,9 +359,9 @@ std::shared_ptr<Module> Module::Interface::GetModule() const {
 Module::Module(Core::System& system) : system(system) {
     using namespace Kernel;
 
-    shared_mem =
-        SharedMemory::Create(nullptr, 0x1000, MemoryPermission::ReadWrite, MemoryPermission::Read,
-                             0, MemoryRegion::BASE, "HID:SharedMemory");
+    shared_mem = system.Kernel().CreateSharedMemory(nullptr, 0x1000, MemoryPermission::ReadWrite,
+                                                    MemoryPermission::Read, 0, MemoryRegion::BASE,
+                                                    "HID:SharedMemory");
 
     // Create event handles
     event_pad_or_touch_1 = system.Kernel().CreateEvent(ResetType::OneShot, "HID:EventPadOrTouch1");
diff --git a/src/core/hle/service/ir/ir_rst.cpp b/src/core/hle/service/ir/ir_rst.cpp
index eb62ddb6c..147c91861 100644
--- a/src/core/hle/service/ir/ir_rst.cpp
+++ b/src/core/hle/service/ir/ir_rst.cpp
@@ -149,9 +149,9 @@ IR_RST::IR_RST(Core::System& system) : ServiceFramework("ir:rst", 1) {
     using namespace Kernel;
     // Note: these two kernel objects are even available before Initialize service function is
     // called.
-    shared_memory =
-        SharedMemory::Create(nullptr, 0x1000, MemoryPermission::ReadWrite, MemoryPermission::Read,
-                             0, MemoryRegion::BASE, "IRRST:SharedMemory");
+    shared_memory = system.Kernel().CreateSharedMemory(nullptr, 0x1000, MemoryPermission::ReadWrite,
+                                                       MemoryPermission::Read, 0,
+                                                       MemoryRegion::BASE, "IRRST:SharedMemory");
     update_event = system.Kernel().CreateEvent(ResetType::OneShot, "IRRST:UpdateEvent");
 
     update_callback_id =