mirror of
https://github.com/RPCS3/rpcs3.git
synced 2025-03-29 22:20:48 +00:00
Fix sys_ppu_thread_start error checking, fix rare bug in sys_ppu_thread_create
* Correct error code to EBUSY. * lv2_obj::awake was called even when EBSUY should be returned. * Fix sys_ppu_thread_create for a newly created thread with the same id as ppu_thread::id_base. (can happen if main thread exited before its creation)
This commit is contained in:
parent
c1dc6838fa
commit
dd6825a7bd
@ -788,14 +788,11 @@ ppu_thread::ppu_thread(const ppu_thread_params& param, std::string_view name, u3
|
|||||||
|
|
||||||
gpr[13] = param.tls_addr;
|
gpr[13] = param.tls_addr;
|
||||||
|
|
||||||
if (detached >= 0 && id != id_base)
|
if (detached >= 0)
|
||||||
{
|
{
|
||||||
// Initialize thread entry point
|
// Initialize thread args
|
||||||
cmd_list
|
gpr[3] = param.arg0;
|
||||||
({
|
gpr[4] = param.arg1;
|
||||||
{ppu_cmd::set_args, 2}, param.arg0, param.arg1,
|
|
||||||
{ppu_cmd::opd_call, 0}, std::bit_cast<u64>(entry_func),
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Trigger the scheduler
|
// Trigger the scheduler
|
||||||
|
@ -15,7 +15,7 @@ void lv2_int_serv::exec()
|
|||||||
({
|
({
|
||||||
{ ppu_cmd::reset_stack, 0 },
|
{ ppu_cmd::reset_stack, 0 },
|
||||||
{ ppu_cmd::set_args, 2 }, arg1, arg2,
|
{ ppu_cmd::set_args, 2 }, arg1, arg2,
|
||||||
{ ppu_cmd::opd_call, 0 }, std::bit_cast<u64>(thread->entry_func),
|
{ ppu_cmd::opd_call, 0 }, thread->entry_func,
|
||||||
{ ppu_cmd::sleep, 0 }
|
{ ppu_cmd::sleep, 0 }
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -441,26 +441,37 @@ error_code sys_ppu_thread_start(ppu_thread& ppu, u32 thread_id)
|
|||||||
{
|
{
|
||||||
sys_ppu_thread.trace("sys_ppu_thread_start(thread_id=0x%x)", thread_id);
|
sys_ppu_thread.trace("sys_ppu_thread_start(thread_id=0x%x)", thread_id);
|
||||||
|
|
||||||
const auto thread = idm::get<named_thread<ppu_thread>>(thread_id, [&](ppu_thread& thread)
|
const auto thread = idm::get<named_thread<ppu_thread>>(thread_id, [&](ppu_thread& thread) -> CellError
|
||||||
{
|
{
|
||||||
if (thread.joiner == ppu_join_status::exited)
|
if (thread.joiner == ppu_join_status::exited)
|
||||||
{
|
{
|
||||||
return false;
|
return CELL_ESRCH;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!thread.state.test_and_reset(cpu_flag::stop))
|
||||||
|
{
|
||||||
|
// Already started
|
||||||
|
return CELL_EBUSY;
|
||||||
}
|
}
|
||||||
|
|
||||||
lv2_obj::awake(&thread);
|
lv2_obj::awake(&thread);
|
||||||
return true;
|
|
||||||
|
thread.cmd_list
|
||||||
|
({
|
||||||
|
{ppu_cmd::opd_call, 0}, thread.entry_func
|
||||||
|
});
|
||||||
|
|
||||||
|
return {};
|
||||||
});
|
});
|
||||||
|
|
||||||
if (!thread || !thread.ret)
|
if (!thread)
|
||||||
{
|
{
|
||||||
return CELL_ESRCH;
|
return CELL_ESRCH;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!thread->state.test_and_reset(cpu_flag::stop))
|
if (thread.ret)
|
||||||
{
|
{
|
||||||
// TODO: what happens there?
|
return thread.ret;
|
||||||
return CELL_EPERM;
|
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
Loading…
x
Reference in New Issue
Block a user