summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorbunnei <bunneidev@gmail.com>2021-04-10 07:10:14 +0200
committerbunnei <bunneidev@gmail.com>2021-05-06 01:40:51 +0200
commitb6156e735cd78d4b7863491ae6bdc63e44404b73 (patch)
treee1ec7753ea7c86223135e2f51b1b1f649af48b90
parenthle: kernel: Ensure all kernel objects with KAutoObject are properly created. (diff)
downloadyuzu-b6156e735cd78d4b7863491ae6bdc63e44404b73.tar
yuzu-b6156e735cd78d4b7863491ae6bdc63e44404b73.tar.gz
yuzu-b6156e735cd78d4b7863491ae6bdc63e44404b73.tar.bz2
yuzu-b6156e735cd78d4b7863491ae6bdc63e44404b73.tar.lz
yuzu-b6156e735cd78d4b7863491ae6bdc63e44404b73.tar.xz
yuzu-b6156e735cd78d4b7863491ae6bdc63e44404b73.tar.zst
yuzu-b6156e735cd78d4b7863491ae6bdc63e44404b73.zip
-rw-r--r--src/core/hle/kernel/k_condition_variable.cpp15
-rw-r--r--src/core/hle/kernel/k_event.cpp4
-rw-r--r--src/core/hle/kernel/k_linked_list.h15
-rw-r--r--src/core/hle/kernel/k_scheduler.cpp4
-rw-r--r--src/core/hle/kernel/k_slab_heap.h1
-rw-r--r--src/core/hle/kernel/kernel.h36
-rw-r--r--src/core/hle/kernel/slab_helpers.h95
7 files changed, 106 insertions, 64 deletions
diff --git a/src/core/hle/kernel/k_condition_variable.cpp b/src/core/hle/kernel/k_condition_variable.cpp
index 930f78974..72565af05 100644
--- a/src/core/hle/kernel/k_condition_variable.cpp
+++ b/src/core/hle/kernel/k_condition_variable.cpp
@@ -185,11 +185,11 @@ KThread* KConditionVariable::SignalImpl(KThread* thread) {
thread->Wakeup();
} else {
// Get the previous owner.
- KThread* owner_thread =
- kernel.CurrentProcess()->GetHandleTable()
- .GetObjectWithoutPseudoHandle<KThread>(
- static_cast<Handle>(prev_tag & ~Svc::HandleWaitMask))
- .ReleasePointerUnsafe();
+ KThread* owner_thread = kernel.CurrentProcess()
+ ->GetHandleTable()
+ .GetObjectWithoutPseudoHandle<KThread>(
+ static_cast<Handle>(prev_tag & ~Svc::HandleWaitMask))
+ .ReleasePointerUnsafe();
if (owner_thread) {
// Add the thread as a waiter on the owner.
@@ -214,7 +214,7 @@ void KConditionVariable::Signal(u64 cv_key, s32 count) {
// Prepare for signaling.
constexpr int MaxThreads = 16;
- KLinkedList<KThread> thread_list;
+ KLinkedList<KThread> thread_list{kernel};
std::array<KThread*, MaxThreads> thread_array;
s32 num_to_close{};
@@ -254,7 +254,8 @@ void KConditionVariable::Signal(u64 cv_key, s32 count) {
}
// Close threads in the list.
- for (auto it = thread_list.begin(); it != thread_list.end(); it = thread_list.erase(it)) {
+ for (auto it = thread_list.begin(); it != thread_list.end();
+ it = thread_list.erase(kernel, it)) {
(*it).Close();
}
}
diff --git a/src/core/hle/kernel/k_event.cpp b/src/core/hle/kernel/k_event.cpp
index bc4a79cc8..4020e5325 100644
--- a/src/core/hle/kernel/k_event.cpp
+++ b/src/core/hle/kernel/k_event.cpp
@@ -21,6 +21,10 @@ void KEvent::Initialize(std::string&& name_) {
// writable events are closed this object will be destroyed.
Open();
+ //// Create our sub events.
+ //KAutoObject::Create(readable_event.get());
+ //KAutoObject::Create(writable_event.get());
+
// Create our sub events.
readable_event = std::make_shared<KReadableEvent>(kernel, name_ + ":Readable");
writable_event = std::make_shared<KWritableEvent>(kernel, name_ + ":Writable");
diff --git a/src/core/hle/kernel/k_linked_list.h b/src/core/hle/kernel/k_linked_list.h
index 8362b6eda..8218bac8d 100644
--- a/src/core/hle/kernel/k_linked_list.h
+++ b/src/core/hle/kernel/k_linked_list.h
@@ -11,6 +11,8 @@
namespace Kernel {
+class KernelCore;
+
class KLinkedListNode : public boost::intrusive::list_base_hook<>,
public KSlabAllocated<KLinkedListNode> {
private:
@@ -118,11 +120,11 @@ public:
};
public:
- constexpr KLinkedList() : BaseList() {}
+ constexpr KLinkedList(KernelCore& kernel_) : BaseList(), kernel{kernel_} {}
~KLinkedList() {
// Erase all elements.
- for (auto it = this->begin(); it != this->end(); it = this->erase(it)) {
+ for (auto it = this->begin(); it != this->end(); it = this->erase(kernel, it)) {
}
// Ensure we succeeded.
@@ -199,7 +201,7 @@ public:
}
iterator insert(const_iterator pos, reference ref) {
- KLinkedListNode* node = KLinkedListNode::Allocate();
+ KLinkedListNode* node = KLinkedListNode::Allocate(kernel);
ASSERT(node != nullptr);
node->Initialize(std::addressof(ref));
return iterator(BaseList::insert(pos.m_base_it, *node));
@@ -221,13 +223,16 @@ public:
this->erase(this->begin());
}
- iterator erase(const iterator pos) {
+ iterator erase(KernelCore& kernel, const iterator pos) {
KLinkedListNode* freed_node = std::addressof(*pos.m_base_it);
iterator ret = iterator(BaseList::erase(pos.m_base_it));
- KLinkedListNode::Free(freed_node);
+ KLinkedListNode::Free(kernel, freed_node);
return ret;
}
+
+private:
+ KernelCore& kernel;
};
} // namespace Kernel
diff --git a/src/core/hle/kernel/k_scheduler.cpp b/src/core/hle/kernel/k_scheduler.cpp
index 09382f7dd..1feda9303 100644
--- a/src/core/hle/kernel/k_scheduler.cpp
+++ b/src/core/hle/kernel/k_scheduler.cpp
@@ -617,7 +617,9 @@ KScheduler::KScheduler(Core::System& system, s32 core_id) : system(system), core
state.highest_priority_thread = nullptr;
}
-KScheduler::~KScheduler() = default;
+KScheduler::~KScheduler() {
+ idle_thread->Close();
+}
KThread* KScheduler::GetCurrentThread() const {
if (auto result = current_thread.load(); result) {
diff --git a/src/core/hle/kernel/k_slab_heap.h b/src/core/hle/kernel/k_slab_heap.h
index a3948cd27..5ce9a1d7c 100644
--- a/src/core/hle/kernel/k_slab_heap.h
+++ b/src/core/hle/kernel/k_slab_heap.h
@@ -97,6 +97,7 @@ public:
void FreeImpl(void* obj) {
// Don't allow freeing an object that wasn't allocated from this heap
ASSERT(Contains(reinterpret_cast<uintptr_t>(obj)));
+
impl.Free(obj);
}
diff --git a/src/core/hle/kernel/kernel.h b/src/core/hle/kernel/kernel.h
index b78602f46..855bb590a 100644
--- a/src/core/hle/kernel/kernel.h
+++ b/src/core/hle/kernel/kernel.h
@@ -11,9 +11,10 @@
#include <vector>
#include "core/arm/cpu_interrupt_handler.h"
#include "core/hardware_properties.h"
+#include "core/hle/kernel/k_auto_object.h"
+#include "core/hle/kernel/k_slab_heap.h"
#include "core/hle/kernel/memory_types.h"
#include "core/hle/kernel/object.h"
-#include "core/hle/kernel/k_auto_object.h"
namespace Core {
class CPUInterruptHandler;
@@ -32,6 +33,8 @@ class ClientPort;
class GlobalSchedulerContext;
class HandleTable;
class KAutoObjectWithListContainer;
+class KEvent;
+class KLinkedListNode;
class KMemoryManager;
class KResourceLimit;
class KScheduler;
@@ -231,9 +234,10 @@ public:
/**
* Creates an HLE service thread, which are used to execute service routines asynchronously.
- * While these are allocated per ServerSession, these need to be owned and managed outside of
- * ServerSession to avoid a circular dependency.
- * @param name String name for the ServerSession creating this thread, used for debug purposes.
+ * While these are allocated per ServerSession, these need to be owned and managed outside
+ * of ServerSession to avoid a circular dependency.
+ * @param name String name for the ServerSession creating this thread, used for debug
+ * purposes.
* @returns The a weak pointer newly created service thread.
*/
std::weak_ptr<Kernel::ServiceThread> CreateServiceThread(const std::string& name);
@@ -252,6 +256,22 @@ public:
Core::System& System();
const Core::System& System() const;
+ /// Gets the slab heap for the specified kernel object type.
+ template <typename T>
+ KSlabHeap<T>& SlabHeap() {
+ if constexpr (std::is_same_v<T, Process>) {
+ return slab_heap_Process;
+ } else if constexpr (std::is_same_v<T, KThread>) {
+ return slab_heap_KThread;
+ } else if constexpr (std::is_same_v<T, KEvent>) {
+ return slab_heap_KEvent;
+ } else if constexpr (std::is_same_v<T, KSharedMemory>) {
+ return slab_heap_KSharedMemory;
+ } else if constexpr (std::is_same_v<T, KLinkedListNode>) {
+ return slab_heap_KLinkedListNode;
+ }
+ }
+
private:
friend class Object;
friend class Process;
@@ -277,7 +297,15 @@ private:
struct Impl;
std::unique_ptr<Impl> impl;
+
bool exception_exited{};
+
+private:
+ KSlabHeap<Process> slab_heap_Process;
+ KSlabHeap<KThread> slab_heap_KThread;
+ KSlabHeap<KEvent> slab_heap_KEvent;
+ KSlabHeap<KSharedMemory> slab_heap_KSharedMemory;
+ KSlabHeap<KLinkedListNode> slab_heap_KLinkedListNode;
};
} // namespace Kernel
diff --git a/src/core/hle/kernel/slab_helpers.h b/src/core/hle/kernel/slab_helpers.h
index ae9d097da..4f23ddabf 100644
--- a/src/core/hle/kernel/slab_helpers.h
+++ b/src/core/hle/kernel/slab_helpers.h
@@ -20,44 +20,44 @@ namespace Kernel {
template <class Derived>
class KSlabAllocated {
-private:
- static inline KSlabHeap<Derived> s_slab_heap;
-
public:
constexpr KSlabAllocated() = default;
- size_t GetSlabIndex() const {
- return s_slab_heap.GetIndex(static_cast<const Derived*>(this));
+ size_t GetSlabIndex(KernelCore& kernel) const {
+ return kernel.SlabHeap<Derived>().GetIndex(static_cast<const Derived*>(this));
}
public:
- static void InitializeSlabHeap(void* memory, size_t memory_size) {
- s_slab_heap.Initialize(memory, memory_size);
+ static void InitializeSlabHeap(KernelCore& kernel, void* memory, size_t memory_size) {
+ kernel.SlabHeap<Derived>().Initialize(memory, memory_size);
}
- static Derived* Allocate() {
- return s_slab_heap.Allocate();
+ static Derived* Allocate(KernelCore& kernel) {
+ return kernel.SlabHeap<Derived>().Allocate();
}
- static void Free(Derived* obj) {
- s_slab_heap.Free(obj);
+ static void Free(KernelCore& kernel, Derived* obj) {
+ kernel.SlabHeap<Derived>().Free(obj);
}
- static size_t GetObjectSize() {
- return s_slab_heap.GetObjectSize();
+ static size_t GetObjectSize(KernelCore& kernel) {
+ return kernel.SlabHeap<Derived>().GetObjectSize();
}
- static size_t GetSlabHeapSize() {
- return s_slab_heap.GetSlabHeapSize();
+
+ static size_t GetSlabHeapSize(KernelCore& kernel) {
+ return kernel.SlabHeap<Derived>().GetSlabHeapSize();
}
- static size_t GetPeakIndex() {
- return s_slab_heap.GetPeakIndex();
+
+ static size_t GetPeakIndex(KernelCore& kernel) {
+ return kernel.SlabHeap<Derived>().GetPeakIndex();
}
- static uintptr_t GetSlabHeapAddress() {
- return s_slab_heap.GetSlabHeapAddress();
+
+ static uintptr_t GetSlabHeapAddress(KernelCore& kernel) {
+ return kernel.SlabHeap<Derived>().GetSlabHeapAddress();
}
- static size_t GetNumRemaining() {
- return s_slab_heap.GetNumRemaining();
+ static size_t GetNumRemaining(KernelCore& kernel) {
+ return kernel.SlabHeap<Derived>().GetNumRemaining();
}
};
@@ -66,43 +66,38 @@ class KAutoObjectWithSlabHeapAndContainer : public Base {
static_assert(std::is_base_of<KAutoObjectWithList, Base>::value);
private:
- static inline KSlabHeap<Derived> s_slab_heap;
- KernelCore& m_kernel;
-
-private:
- static Derived* Allocate() {
- return s_slab_heap.Allocate();
+ static Derived* Allocate(KernelCore& kernel) {
+ return kernel.SlabHeap<Derived>().Allocate();
}
static Derived* AllocateWithKernel(KernelCore& kernel) {
- return s_slab_heap.AllocateWithKernel(kernel);
+ return kernel.SlabHeap<Derived>().AllocateWithKernel(kernel);
}
- static void Free(Derived* obj) {
- s_slab_heap.Free(obj);
+ static void Free(KernelCore& kernel, Derived* obj) {
+ kernel.SlabHeap<Derived>().Free(obj);
}
public:
class ListAccessor : public KAutoObjectWithListContainer::ListAccessor {
public:
- ListAccessor()
- : KAutoObjectWithListContainer::ListAccessor(m_kernel.ObjectListContainer()) {}
+ ListAccessor() : KAutoObjectWithListContainer::ListAccessor(kernel.ObjectListContainer()) {}
~ListAccessor() = default;
};
public:
- KAutoObjectWithSlabHeapAndContainer(KernelCore& kernel) : Base(kernel), m_kernel(kernel) {}
+ KAutoObjectWithSlabHeapAndContainer(KernelCore& kernel_) : Base(kernel_), kernel(kernel_) {}
virtual ~KAutoObjectWithSlabHeapAndContainer() {}
virtual void Destroy() override {
const bool is_initialized = this->IsInitialized();
uintptr_t arg = 0;
if (is_initialized) {
- m_kernel.ObjectListContainer().Unregister(this);
+ kernel.ObjectListContainer().Unregister(this);
arg = this->GetPostDestroyArgument();
this->Finalize();
}
- Free(static_cast<Derived*>(this));
+ Free(kernel, static_cast<Derived*>(this));
if (is_initialized) {
Derived::PostDestroy(arg);
}
@@ -116,12 +111,12 @@ public:
}
size_t GetSlabIndex() const {
- return s_slab_heap.GetObjectIndex(static_cast<const Derived*>(this));
+ return SlabHeap<Derived>(kernel).GetObjectIndex(static_cast<const Derived*>(this));
}
public:
static void InitializeSlabHeap(KernelCore& kernel, void* memory, size_t memory_size) {
- s_slab_heap.Initialize(memory, memory_size);
+ kernel.SlabHeap<Derived>().Initialize(memory, memory_size);
kernel.ObjectListContainer().Initialize();
}
@@ -145,22 +140,28 @@ public:
return kernel.ObjectListContainer().Register(obj);
}
- static size_t GetObjectSize() {
- return s_slab_heap.GetObjectSize();
+ static size_t GetObjectSize(KernelCore& kernel) {
+ return kernel.SlabHeap<Derived>().GetObjectSize();
}
- static size_t GetSlabHeapSize() {
- return s_slab_heap.GetSlabHeapSize();
+
+ static size_t GetSlabHeapSize(KernelCore& kernel) {
+ return kernel.SlabHeap<Derived>().GetSlabHeapSize();
}
- static size_t GetPeakIndex() {
- return s_slab_heap.GetPeakIndex();
+
+ static size_t GetPeakIndex(KernelCore& kernel) {
+ return kernel.SlabHeap<Derived>().GetPeakIndex();
}
- static uintptr_t GetSlabHeapAddress() {
- return s_slab_heap.GetSlabHeapAddress();
+
+ static uintptr_t GetSlabHeapAddress(KernelCore& kernel) {
+ return kernel.SlabHeap<Derived>().GetSlabHeapAddress();
}
- static size_t GetNumRemaining() {
- return s_slab_heap.GetNumRemaining();
+ static size_t GetNumRemaining(KernelCore& kernel) {
+ return kernel.SlabHeap<Derived>().GetNumRemaining();
}
+
+protected:
+ KernelCore& kernel;
};
} // namespace Kernel