lv2: Wait for rescheduling before confirming timeouts (#7875)
This commit is contained in:
@@ -291,12 +291,17 @@ error_code sys_event_queue_receive(ppu_thread& ppu, u32 equeue_id, vm::ptr<sys_e
|
|||||||
{
|
{
|
||||||
if (lv2_obj::wait_timeout(timeout, &ppu))
|
if (lv2_obj::wait_timeout(timeout, &ppu))
|
||||||
{
|
{
|
||||||
|
// Wait for rescheduling
|
||||||
|
if (ppu.check_state())
|
||||||
|
{
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
std::lock_guard lock(queue->mutex);
|
std::lock_guard lock(queue->mutex);
|
||||||
|
|
||||||
if (!queue->unqueue(queue->sq, &ppu))
|
if (!queue->unqueue(queue->sq, &ppu))
|
||||||
{
|
{
|
||||||
timeout = 0;
|
break;
|
||||||
continue;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
ppu.gpr[3] = CELL_ETIMEDOUT;
|
ppu.gpr[3] = CELL_ETIMEDOUT;
|
||||||
|
|||||||
@@ -170,12 +170,17 @@ error_code sys_event_flag_wait(ppu_thread& ppu, u32 id, u64 bitptn, u32 mode, vm
|
|||||||
{
|
{
|
||||||
if (lv2_obj::wait_timeout(timeout, &ppu))
|
if (lv2_obj::wait_timeout(timeout, &ppu))
|
||||||
{
|
{
|
||||||
|
// Wait for rescheduling
|
||||||
|
if (ppu.check_state())
|
||||||
|
{
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
std::lock_guard lock(flag->mutex);
|
std::lock_guard lock(flag->mutex);
|
||||||
|
|
||||||
if (!flag->unqueue(flag->sq, &ppu))
|
if (!flag->unqueue(flag->sq, &ppu))
|
||||||
{
|
{
|
||||||
timeout = 0;
|
break;
|
||||||
continue;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
flag->waiters--;
|
flag->waiters--;
|
||||||
|
|||||||
@@ -356,18 +356,31 @@ error_code _sys_lwcond_queue_wait(ppu_thread& ppu, u32 lwcond_id, u32 lwmutex_id
|
|||||||
{
|
{
|
||||||
if (lv2_obj::wait_timeout(timeout, &ppu))
|
if (lv2_obj::wait_timeout(timeout, &ppu))
|
||||||
{
|
{
|
||||||
std::lock_guard lock(cond->mutex);
|
// Wait for rescheduling
|
||||||
|
if (ppu.check_state())
|
||||||
if (!cond->unqueue(cond->sq, &ppu))
|
|
||||||
{
|
{
|
||||||
timeout = 0;
|
return 0;
|
||||||
continue;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
cond->waiters--;
|
std::lock_guard lock(cond->mutex);
|
||||||
|
|
||||||
ppu.gpr[3] = CELL_ETIMEDOUT;
|
if (cond->unqueue(cond->sq, &ppu))
|
||||||
break;
|
{
|
||||||
|
cond->waiters--;
|
||||||
|
ppu.gpr[3] = CELL_ETIMEDOUT;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::lock_guard lock2(mutex->mutex);
|
||||||
|
|
||||||
|
if (std::find(mutex->sq.cbegin(), mutex->sq.cend(), &ppu) == mutex->sq.cend())
|
||||||
|
{
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
mutex->sleep(ppu);
|
||||||
|
timeout = 0;
|
||||||
|
continue;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
|
|||||||
@@ -164,12 +164,17 @@ error_code _sys_lwmutex_lock(ppu_thread& ppu, u32 lwmutex_id, u64 timeout)
|
|||||||
{
|
{
|
||||||
if (lv2_obj::wait_timeout(timeout, &ppu))
|
if (lv2_obj::wait_timeout(timeout, &ppu))
|
||||||
{
|
{
|
||||||
|
// Wait for rescheduling
|
||||||
|
if (ppu.check_state())
|
||||||
|
{
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
std::lock_guard lock(mutex->mutex);
|
std::lock_guard lock(mutex->mutex);
|
||||||
|
|
||||||
if (!mutex->unqueue(mutex->sq, &ppu))
|
if (!mutex->unqueue(mutex->sq, &ppu))
|
||||||
{
|
{
|
||||||
timeout = 0;
|
break;
|
||||||
continue;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
ppu.gpr[3] = CELL_ETIMEDOUT;
|
ppu.gpr[3] = CELL_ETIMEDOUT;
|
||||||
|
|||||||
@@ -164,12 +164,17 @@ error_code sys_mutex_lock(ppu_thread& ppu, u32 mutex_id, u64 timeout)
|
|||||||
{
|
{
|
||||||
if (lv2_obj::wait_timeout(timeout, &ppu))
|
if (lv2_obj::wait_timeout(timeout, &ppu))
|
||||||
{
|
{
|
||||||
|
// Wait for rescheduling
|
||||||
|
if (ppu.check_state())
|
||||||
|
{
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
std::lock_guard lock(mutex->mutex);
|
std::lock_guard lock(mutex->mutex);
|
||||||
|
|
||||||
if (!mutex->unqueue(mutex->sq, &ppu))
|
if (!mutex->unqueue(mutex->sq, &ppu))
|
||||||
{
|
{
|
||||||
timeout = 0;
|
break;
|
||||||
continue;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
ppu.gpr[3] = CELL_ETIMEDOUT;
|
ppu.gpr[3] = CELL_ETIMEDOUT;
|
||||||
|
|||||||
@@ -1889,12 +1889,17 @@ error_code sys_net_bnet_poll(ppu_thread& ppu, vm::ptr<sys_net_pollfd> fds, s32 n
|
|||||||
{
|
{
|
||||||
if (lv2_obj::wait_timeout(timeout, &ppu))
|
if (lv2_obj::wait_timeout(timeout, &ppu))
|
||||||
{
|
{
|
||||||
|
// Wait for rescheduling
|
||||||
|
if (ppu.check_state())
|
||||||
|
{
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
std::lock_guard nw_lock(g_fxo->get<network_context>()->s_nw_mutex);
|
std::lock_guard nw_lock(g_fxo->get<network_context>()->s_nw_mutex);
|
||||||
|
|
||||||
if (signaled)
|
if (signaled)
|
||||||
{
|
{
|
||||||
timeout = 0;
|
break;
|
||||||
continue;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
network_clear_queue(ppu);
|
network_clear_queue(ppu);
|
||||||
@@ -2080,12 +2085,17 @@ error_code sys_net_bnet_select(ppu_thread& ppu, s32 nfds, vm::ptr<sys_net_fd_set
|
|||||||
{
|
{
|
||||||
if (lv2_obj::wait_timeout(timeout, &ppu))
|
if (lv2_obj::wait_timeout(timeout, &ppu))
|
||||||
{
|
{
|
||||||
|
// Wait for rescheduling
|
||||||
|
if (ppu.check_state())
|
||||||
|
{
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
std::lock_guard nw_lock(g_fxo->get<network_context>()->s_nw_mutex);
|
std::lock_guard nw_lock(g_fxo->get<network_context>()->s_nw_mutex);
|
||||||
|
|
||||||
if (signaled)
|
if (signaled)
|
||||||
{
|
{
|
||||||
timeout = 0;
|
break;
|
||||||
continue;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
network_clear_queue(ppu);
|
network_clear_queue(ppu);
|
||||||
|
|||||||
@@ -139,12 +139,17 @@ error_code sys_rwlock_rlock(ppu_thread& ppu, u32 rw_lock_id, u64 timeout)
|
|||||||
{
|
{
|
||||||
if (lv2_obj::wait_timeout(timeout, &ppu))
|
if (lv2_obj::wait_timeout(timeout, &ppu))
|
||||||
{
|
{
|
||||||
|
// Wait for rescheduling
|
||||||
|
if (ppu.check_state())
|
||||||
|
{
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
std::lock_guard lock(rwlock->mutex);
|
std::lock_guard lock(rwlock->mutex);
|
||||||
|
|
||||||
if (!rwlock->unqueue(rwlock->rq, &ppu))
|
if (!rwlock->unqueue(rwlock->rq, &ppu))
|
||||||
{
|
{
|
||||||
timeout = 0;
|
break;
|
||||||
continue;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
ppu.gpr[3] = CELL_ETIMEDOUT;
|
ppu.gpr[3] = CELL_ETIMEDOUT;
|
||||||
@@ -336,12 +341,17 @@ error_code sys_rwlock_wlock(ppu_thread& ppu, u32 rw_lock_id, u64 timeout)
|
|||||||
{
|
{
|
||||||
if (lv2_obj::wait_timeout(timeout, &ppu))
|
if (lv2_obj::wait_timeout(timeout, &ppu))
|
||||||
{
|
{
|
||||||
|
// Wait for rescheduling
|
||||||
|
if (ppu.check_state())
|
||||||
|
{
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
std::lock_guard lock(rwlock->mutex);
|
std::lock_guard lock(rwlock->mutex);
|
||||||
|
|
||||||
if (!rwlock->unqueue(rwlock->wq, &ppu))
|
if (!rwlock->unqueue(rwlock->wq, &ppu))
|
||||||
{
|
{
|
||||||
timeout = 0;
|
break;
|
||||||
continue;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// If the last waiter quit the writer sleep queue, wake blocked readers
|
// If the last waiter quit the writer sleep queue, wake blocked readers
|
||||||
|
|||||||
@@ -130,12 +130,17 @@ error_code sys_semaphore_wait(ppu_thread& ppu, u32 sem_id, u64 timeout)
|
|||||||
{
|
{
|
||||||
if (lv2_obj::wait_timeout(timeout, &ppu))
|
if (lv2_obj::wait_timeout(timeout, &ppu))
|
||||||
{
|
{
|
||||||
|
// Wait for rescheduling
|
||||||
|
if (ppu.check_state())
|
||||||
|
{
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
std::lock_guard lock(sem->mutex);
|
std::lock_guard lock(sem->mutex);
|
||||||
|
|
||||||
if (!sem->unqueue(sem->sq, &ppu))
|
if (!sem->unqueue(sem->sq, &ppu))
|
||||||
{
|
{
|
||||||
timeout = 0;
|
break;
|
||||||
continue;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
verify(HERE), 0 > sem->val.fetch_op([](s32& val)
|
verify(HERE), 0 > sem->val.fetch_op([](s32& val)
|
||||||
|
|||||||
Reference in New Issue
Block a user