mirror of
				https://git.suyu.dev/suyu/suyu
				synced 2025-11-04 08:59:03 -06:00 
			
		
		
		
	Kernel: Use different thread statuses when a thread calls WaitSynchronization1 and WaitSynchronizationN with wait_all = true.
This commit removes the overly general THREADSTATUS_WAIT_SYNCH and replaces it with two more granular statuses: THREADSTATUS_WAIT_SYNCH_ANY when a thread waits on objects via WaitSynchronization1 or WaitSynchronizationN with wait_all = false. THREADSTATUS_WAIT_SYNCH_ALL when a thread waits on objects via WaitSynchronizationN with wait_all = true.
This commit is contained in:
		@@ -72,7 +72,8 @@ Thread* GetCurrentThread() {
 | 
			
		||||
 * @return True if the thread is waiting, false otherwise
 | 
			
		||||
 */
 | 
			
		||||
static bool CheckWait_WaitObject(const Thread* thread, WaitObject* wait_object) {
 | 
			
		||||
    if (thread->status != THREADSTATUS_WAIT_SYNCH)
 | 
			
		||||
    if (thread->status != THREADSTATUS_WAIT_SYNCH_ALL &&
 | 
			
		||||
        thread->status != THREADSTATUS_WAIT_SYNCH_ANY)
 | 
			
		||||
        return false;
 | 
			
		||||
 | 
			
		||||
    auto itr = std::find(thread->wait_objects.begin(), thread->wait_objects.end(), wait_object);
 | 
			
		||||
@@ -253,7 +254,7 @@ void WaitCurrentThread_WaitSynchronization(std::vector<SharedPtr<WaitObject>> wa
 | 
			
		||||
    Thread* thread = GetCurrentThread();
 | 
			
		||||
    thread->wait_set_output = wait_set_output;
 | 
			
		||||
    thread->wait_objects = std::move(wait_objects);
 | 
			
		||||
    thread->status = THREADSTATUS_WAIT_SYNCH;
 | 
			
		||||
    thread->status = THREADSTATUS_WAIT_SYNCH_ANY;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void WaitCurrentThread_ArbitrateAddress(VAddr wait_address) {
 | 
			
		||||
@@ -281,7 +282,8 @@ static void ThreadWakeupCallback(u64 thread_handle, int cycles_late) {
 | 
			
		||||
        return;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    if (thread->status == THREADSTATUS_WAIT_SYNCH || thread->status == THREADSTATUS_WAIT_ARB) {
 | 
			
		||||
    if (thread->status == THREADSTATUS_WAIT_SYNCH_ANY ||
 | 
			
		||||
        thread->status == THREADSTATUS_WAIT_SYNCH_ALL || thread->status == THREADSTATUS_WAIT_ARB) {
 | 
			
		||||
        thread->wait_set_output = false;
 | 
			
		||||
        // Remove the thread from each of its waiting objects' waitlists
 | 
			
		||||
        for (auto& object : thread->wait_objects)
 | 
			
		||||
@@ -306,7 +308,8 @@ void Thread::WakeAfterDelay(s64 nanoseconds) {
 | 
			
		||||
 | 
			
		||||
void Thread::ResumeFromWait() {
 | 
			
		||||
    switch (status) {
 | 
			
		||||
    case THREADSTATUS_WAIT_SYNCH:
 | 
			
		||||
    case THREADSTATUS_WAIT_SYNCH_ALL:
 | 
			
		||||
    case THREADSTATUS_WAIT_SYNCH_ANY:
 | 
			
		||||
    case THREADSTATUS_WAIT_ARB:
 | 
			
		||||
    case THREADSTATUS_WAIT_SLEEP:
 | 
			
		||||
        break;
 | 
			
		||||
 
 | 
			
		||||
@@ -31,13 +31,14 @@ enum ThreadProcessorId : s32 {
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
enum ThreadStatus {
 | 
			
		||||
    THREADSTATUS_RUNNING,    ///< Currently running
 | 
			
		||||
    THREADSTATUS_READY,      ///< Ready to run
 | 
			
		||||
    THREADSTATUS_WAIT_ARB,   ///< Waiting on an address arbiter
 | 
			
		||||
    THREADSTATUS_WAIT_SLEEP, ///< Waiting due to a SleepThread SVC
 | 
			
		||||
    THREADSTATUS_WAIT_SYNCH, ///< Waiting due to a WaitSynchronization SVC
 | 
			
		||||
    THREADSTATUS_DORMANT,    ///< Created but not yet made ready
 | 
			
		||||
    THREADSTATUS_DEAD        ///< Run to completion, or forcefully terminated
 | 
			
		||||
    THREADSTATUS_RUNNING,        ///< Currently running
 | 
			
		||||
    THREADSTATUS_READY,          ///< Ready to run
 | 
			
		||||
    THREADSTATUS_WAIT_ARB,       ///< Waiting on an address arbiter
 | 
			
		||||
    THREADSTATUS_WAIT_SLEEP,     ///< Waiting due to a SleepThread SVC
 | 
			
		||||
    THREADSTATUS_WAIT_SYNCH_ANY, ///< Waiting due to WaitSynch1 or WaitSynchN with wait_all = false
 | 
			
		||||
    THREADSTATUS_WAIT_SYNCH_ALL, ///< Waiting due to WaitSynchronizationN with wait_all = true
 | 
			
		||||
    THREADSTATUS_DORMANT,        ///< Created but not yet made ready
 | 
			
		||||
    THREADSTATUS_DEAD            ///< Run to completion, or forcefully terminated
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
namespace Kernel {
 | 
			
		||||
@@ -158,10 +159,10 @@ public:
 | 
			
		||||
    /**
 | 
			
		||||
     * Returns whether this thread is waiting for all the objects in
 | 
			
		||||
     * its wait list to become ready, as a result of a WaitSynchronizationN call
 | 
			
		||||
     * with wait_all = true, or a ReplyAndReceive call.
 | 
			
		||||
     * with wait_all = true.
 | 
			
		||||
     */
 | 
			
		||||
    bool IsSleepingOnWaitAll() const {
 | 
			
		||||
        return !wait_objects.empty();
 | 
			
		||||
        return status == THREADSTATUS_WAIT_SYNCH_ALL;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    ARM_Interface::ThreadContext context;
 | 
			
		||||
 
 | 
			
		||||
@@ -278,7 +278,7 @@ static ResultCode WaitSynchronization1(Kernel::Handle handle, s64 nano_seconds)
 | 
			
		||||
            return ERR_SYNC_TIMEOUT;
 | 
			
		||||
 | 
			
		||||
        object->AddWaitingThread(thread);
 | 
			
		||||
        thread->status = THREADSTATUS_WAIT_SYNCH;
 | 
			
		||||
        thread->status = THREADSTATUS_WAIT_SYNCH_ANY;
 | 
			
		||||
 | 
			
		||||
        // Create an event to wake the thread up after the specified nanosecond delay has passed
 | 
			
		||||
        thread->WakeAfterDelay(nano_seconds);
 | 
			
		||||
@@ -351,7 +351,7 @@ static ResultCode WaitSynchronizationN(s32* out, Kernel::Handle* handles, s32 ha
 | 
			
		||||
            return ERR_SYNC_TIMEOUT;
 | 
			
		||||
 | 
			
		||||
        // Put the thread to sleep
 | 
			
		||||
        thread->status = THREADSTATUS_WAIT_SYNCH;
 | 
			
		||||
        thread->status = THREADSTATUS_WAIT_SYNCH_ALL;
 | 
			
		||||
 | 
			
		||||
        // Add the thread to each of the objects' waiting threads.
 | 
			
		||||
        for (auto& object : objects) {
 | 
			
		||||
@@ -393,7 +393,7 @@ static ResultCode WaitSynchronizationN(s32* out, Kernel::Handle* handles, s32 ha
 | 
			
		||||
            return ERR_SYNC_TIMEOUT;
 | 
			
		||||
 | 
			
		||||
        // Put the thread to sleep
 | 
			
		||||
        thread->status = THREADSTATUS_WAIT_SYNCH;
 | 
			
		||||
        thread->status = THREADSTATUS_WAIT_SYNCH_ANY;
 | 
			
		||||
 | 
			
		||||
        // Clear the thread's waitlist, we won't use it for wait_all = false
 | 
			
		||||
        thread->wait_objects.clear();
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user