diff options
Diffstat (limited to 'src/core')
| -rw-r--r-- | src/core/hle/kernel/thread.cpp | 34 |
1 files changed, 15 insertions, 19 deletions
diff --git a/src/core/hle/kernel/thread.cpp b/src/core/hle/kernel/thread.cpp index 2521f883d..f3f54a4e9 100644 --- a/src/core/hle/kernel/thread.cpp +++ b/src/core/hle/kernel/thread.cpp | |||
| @@ -35,16 +35,16 @@ public: | |||
| 35 | inline bool IsSuspended() const { return (status & THREADSTATUS_SUSPEND) != 0; } | 35 | inline bool IsSuspended() const { return (status & THREADSTATUS_SUSPEND) != 0; } |
| 36 | 36 | ||
| 37 | ResultVal<bool> WaitSynchronization() override { | 37 | ResultVal<bool> WaitSynchronization() override { |
| 38 | if (status != THREADSTATUS_DORMANT) { | 38 | const bool wait = status != THREADSTATUS_DORMANT; |
| 39 | if (wait) { | ||
| 39 | Handle thread = GetCurrentThreadHandle(); | 40 | Handle thread = GetCurrentThreadHandle(); |
| 40 | if (std::find(waiting_threads.begin(), waiting_threads.end(), thread) == waiting_threads.end()) { | 41 | if (std::find(waiting_threads.begin(), waiting_threads.end(), thread) == waiting_threads.end()) { |
| 41 | waiting_threads.push_back(thread); | 42 | waiting_threads.push_back(thread); |
| 42 | } | 43 | } |
| 43 | WaitCurrentThread(WAITTYPE_THREADEND, this->GetHandle()); | 44 | WaitCurrentThread(WAITTYPE_THREADEND, this->GetHandle()); |
| 44 | return MakeResult<bool>(true); | ||
| 45 | } else { | ||
| 46 | return MakeResult<bool>(false); | ||
| 47 | } | 45 | } |
| 46 | |||
| 47 | return MakeResult<bool>(wait); | ||
| 48 | } | 48 | } |
| 49 | 49 | ||
| 50 | ThreadContext context; | 50 | ThreadContext context; |
| @@ -141,14 +141,9 @@ void ChangeReadyState(Thread* t, bool ready) { | |||
| 141 | } | 141 | } |
| 142 | 142 | ||
| 143 | /// Verify that a thread has not been released from waiting | 143 | /// Verify that a thread has not been released from waiting |
| 144 | inline bool VerifyWait(Handle handle, WaitType type, Handle wait_handle) { | 144 | inline bool VerifyWait(const Thread* thread, WaitType type, Handle wait_handle) { |
| 145 | Thread* thread = g_object_pool.Get<Thread>(handle); | ||
| 146 | _dbg_assert_(KERNEL, thread != nullptr); | 145 | _dbg_assert_(KERNEL, thread != nullptr); |
| 147 | 146 | return type == thread->wait_type && wait_handle == thread->wait_handle; | |
| 148 | if (type != thread->wait_type || wait_handle != thread->wait_handle) | ||
| 149 | return false; | ||
| 150 | |||
| 151 | return true; | ||
| 152 | } | 147 | } |
| 153 | 148 | ||
| 154 | /// Stops the current thread | 149 | /// Stops the current thread |
| @@ -158,10 +153,10 @@ ResultCode StopThread(Handle handle, const char* reason) { | |||
| 158 | 153 | ||
| 159 | ChangeReadyState(thread, false); | 154 | ChangeReadyState(thread, false); |
| 160 | thread->status = THREADSTATUS_DORMANT; | 155 | thread->status = THREADSTATUS_DORMANT; |
| 161 | for (size_t i = 0; i < thread->waiting_threads.size(); ++i) { | 156 | for (Handle waiting_handle : thread->waiting_threads) { |
| 162 | const Handle waiting_thread = thread->waiting_threads[i]; | 157 | Thread* waiting_thread = g_object_pool.Get<Thread>(waiting_handle); |
| 163 | if (VerifyWait(waiting_thread, WAITTYPE_THREADEND, handle)) { | 158 | if (VerifyWait(waiting_thread, WAITTYPE_THREADEND, handle)) { |
| 164 | ResumeThreadFromWait(waiting_thread); | 159 | ResumeThreadFromWait(waiting_handle); |
| 165 | } | 160 | } |
| 166 | } | 161 | } |
| 167 | thread->waiting_threads.clear(); | 162 | thread->waiting_threads.clear(); |
| @@ -194,13 +189,13 @@ Handle ArbitrateHighestPriorityThread(u32 arbiter, u32 address) { | |||
| 194 | s32 priority = THREADPRIO_LOWEST; | 189 | s32 priority = THREADPRIO_LOWEST; |
| 195 | 190 | ||
| 196 | // Iterate through threads, find highest priority thread that is waiting to be arbitrated... | 191 | // Iterate through threads, find highest priority thread that is waiting to be arbitrated... |
| 197 | for (const auto& handle : thread_queue) { | 192 | for (Handle handle : thread_queue) { |
| 193 | Thread* thread = g_object_pool.Get<Thread>(handle); | ||
| 198 | 194 | ||
| 199 | // TODO(bunnei): Verify arbiter address... | 195 | // TODO(bunnei): Verify arbiter address... |
| 200 | if (!VerifyWait(handle, WAITTYPE_ARB, arbiter)) | 196 | if (!VerifyWait(thread, WAITTYPE_ARB, arbiter)) |
| 201 | continue; | 197 | continue; |
| 202 | 198 | ||
| 203 | Thread* thread = g_object_pool.Get<Thread>(handle); | ||
| 204 | if (thread == nullptr) | 199 | if (thread == nullptr) |
| 205 | continue; // TODO(yuriks): Thread handle will hang around forever. Should clean up. | 200 | continue; // TODO(yuriks): Thread handle will hang around forever. Should clean up. |
| 206 | if(thread->current_priority <= priority) { | 201 | if(thread->current_priority <= priority) { |
| @@ -219,10 +214,11 @@ Handle ArbitrateHighestPriorityThread(u32 arbiter, u32 address) { | |||
| 219 | void ArbitrateAllThreads(u32 arbiter, u32 address) { | 214 | void ArbitrateAllThreads(u32 arbiter, u32 address) { |
| 220 | 215 | ||
| 221 | // Iterate through threads, find highest priority thread that is waiting to be arbitrated... | 216 | // Iterate through threads, find highest priority thread that is waiting to be arbitrated... |
| 222 | for (const auto& handle : thread_queue) { | 217 | for (Handle handle : thread_queue) { |
| 218 | Thread* thread = g_object_pool.Get<Thread>(handle); | ||
| 223 | 219 | ||
| 224 | // TODO(bunnei): Verify arbiter address... | 220 | // TODO(bunnei): Verify arbiter address... |
| 225 | if (VerifyWait(handle, WAITTYPE_ARB, arbiter)) | 221 | if (VerifyWait(thread, WAITTYPE_ARB, arbiter)) |
| 226 | ResumeThreadFromWait(handle); | 222 | ResumeThreadFromWait(handle); |
| 227 | } | 223 | } |
| 228 | } | 224 | } |