Merge pull request #5871 from lioncash/address-arb

k_address_arbiter: Minor cleanup
This commit is contained in:
bunnei 2021-02-06 13:05:19 -08:00 committed by GitHub
commit 9078f4a9c7
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23

View File

@ -118,9 +118,10 @@ ResultCode KAddressArbiter::SignalAndIncrementIfEqual(VAddr addr, s32 value, s32
// Check the userspace value. // Check the userspace value.
s32 user_value{}; s32 user_value{};
R_UNLESS(UpdateIfEqual(system, std::addressof(user_value), addr, value, value + 1), if (!UpdateIfEqual(system, &user_value, addr, value, value + 1)) {
Svc::ResultInvalidCurrentMemory); LOG_ERROR(Kernel, "Invalid current memory!");
return Svc::ResultInvalidCurrentMemory;
}
if (user_value != value) { if (user_value != value) {
return Svc::ResultInvalidState; return Svc::ResultInvalidState;
} }
@ -146,25 +147,23 @@ ResultCode KAddressArbiter::SignalAndModifyByWaitingCountIfEqual(VAddr addr, s32
// Perform signaling. // Perform signaling.
s32 num_waiters{}; s32 num_waiters{};
{ {
KScopedSchedulerLock sl(kernel); [[maybe_unused]] const KScopedSchedulerLock sl(kernel);
auto it = thread_tree.nfind_light({addr, -1}); auto it = thread_tree.nfind_light({addr, -1});
// Determine the updated value. // Determine the updated value.
s32 new_value{}; s32 new_value{};
if (/*GetTargetFirmware() >= TargetFirmware_7_0_0*/ true) {
if (count <= 0) { if (count <= 0) {
if ((it != thread_tree.end()) && (it->GetAddressArbiterKey() == addr)) { if (it != thread_tree.end() && it->GetAddressArbiterKey() == addr) {
new_value = value - 2; new_value = value - 2;
} else { } else {
new_value = value + 1; new_value = value + 1;
} }
} else { } else {
if ((it != thread_tree.end()) && (it->GetAddressArbiterKey() == addr)) { if (it != thread_tree.end() && it->GetAddressArbiterKey() == addr) {
auto tmp_it = it; auto tmp_it = it;
s32 tmp_num_waiters{}; s32 tmp_num_waiters{};
while ((++tmp_it != thread_tree.end()) && while (++tmp_it != thread_tree.end() && tmp_it->GetAddressArbiterKey() == addr) {
(tmp_it->GetAddressArbiterKey() == addr)) { if (tmp_num_waiters++ >= count) {
if ((tmp_num_waiters++) >= count) {
break; break;
} }
} }
@ -178,43 +177,20 @@ ResultCode KAddressArbiter::SignalAndModifyByWaitingCountIfEqual(VAddr addr, s32
new_value = value + 1; new_value = value + 1;
} }
} }
} else {
if (count <= 0) {
if ((it != thread_tree.end()) && (it->GetAddressArbiterKey() == addr)) {
new_value = value - 1;
} else {
new_value = value + 1;
}
} else {
auto tmp_it = it;
s32 tmp_num_waiters{};
while ((tmp_it != thread_tree.end()) && (tmp_it->GetAddressArbiterKey() == addr) &&
(tmp_num_waiters < count + 1)) {
++tmp_num_waiters;
++tmp_it;
}
if (tmp_num_waiters == 0) {
new_value = value + 1;
} else if (tmp_num_waiters <= count) {
new_value = value - 1;
} else {
new_value = value;
}
}
}
// Check the userspace value. // Check the userspace value.
s32 user_value{}; s32 user_value{};
bool succeeded{}; bool succeeded{};
if (value != new_value) { if (value != new_value) {
succeeded = UpdateIfEqual(system, std::addressof(user_value), addr, value, new_value); succeeded = UpdateIfEqual(system, &user_value, addr, value, new_value);
} else { } else {
succeeded = ReadFromUser(system, std::addressof(user_value), addr); succeeded = ReadFromUser(system, &user_value, addr);
} }
R_UNLESS(succeeded, Svc::ResultInvalidCurrentMemory); if (!succeeded) {
LOG_ERROR(Kernel, "Invalid current memory!");
return Svc::ResultInvalidCurrentMemory;
}
if (user_value != value) { if (user_value != value) {
return Svc::ResultInvalidState; return Svc::ResultInvalidState;
} }
@ -255,9 +231,9 @@ ResultCode KAddressArbiter::WaitIfLessThan(VAddr addr, s32 value, bool decrement
s32 user_value{}; s32 user_value{};
bool succeeded{}; bool succeeded{};
if (decrement) { if (decrement) {
succeeded = DecrementIfLessThan(system, std::addressof(user_value), addr, value); succeeded = DecrementIfLessThan(system, &user_value, addr, value);
} else { } else {
succeeded = ReadFromUser(system, std::addressof(user_value), addr); succeeded = ReadFromUser(system, &user_value, addr);
} }
if (!succeeded) { if (!succeeded) {
@ -278,7 +254,7 @@ ResultCode KAddressArbiter::WaitIfLessThan(VAddr addr, s32 value, bool decrement
} }
// Set the arbiter. // Set the arbiter.
cur_thread->SetAddressArbiter(std::addressof(thread_tree), addr); cur_thread->SetAddressArbiter(&thread_tree, addr);
thread_tree.insert(*cur_thread); thread_tree.insert(*cur_thread);
cur_thread->SetState(ThreadState::Waiting); cur_thread->SetState(ThreadState::Waiting);
cur_thread->SetWaitReasonForDebugging(ThreadWaitReasonForDebugging::Arbitration); cur_thread->SetWaitReasonForDebugging(ThreadWaitReasonForDebugging::Arbitration);
@ -299,7 +275,7 @@ ResultCode KAddressArbiter::WaitIfLessThan(VAddr addr, s32 value, bool decrement
// Get the result. // Get the result.
KSynchronizationObject* dummy{}; KSynchronizationObject* dummy{};
return cur_thread->GetWaitResult(std::addressof(dummy)); return cur_thread->GetWaitResult(&dummy);
} }
ResultCode KAddressArbiter::WaitIfEqual(VAddr addr, s32 value, s64 timeout) { ResultCode KAddressArbiter::WaitIfEqual(VAddr addr, s32 value, s64 timeout) {
@ -320,7 +296,7 @@ ResultCode KAddressArbiter::WaitIfEqual(VAddr addr, s32 value, s64 timeout) {
// Read the value from userspace. // Read the value from userspace.
s32 user_value{}; s32 user_value{};
if (!ReadFromUser(system, std::addressof(user_value), addr)) { if (!ReadFromUser(system, &user_value, addr)) {
slp.CancelSleep(); slp.CancelSleep();
return Svc::ResultInvalidCurrentMemory; return Svc::ResultInvalidCurrentMemory;
} }
@ -338,7 +314,7 @@ ResultCode KAddressArbiter::WaitIfEqual(VAddr addr, s32 value, s64 timeout) {
} }
// Set the arbiter. // Set the arbiter.
cur_thread->SetAddressArbiter(std::addressof(thread_tree), addr); cur_thread->SetAddressArbiter(&thread_tree, addr);
thread_tree.insert(*cur_thread); thread_tree.insert(*cur_thread);
cur_thread->SetState(ThreadState::Waiting); cur_thread->SetState(ThreadState::Waiting);
cur_thread->SetWaitReasonForDebugging(ThreadWaitReasonForDebugging::Arbitration); cur_thread->SetWaitReasonForDebugging(ThreadWaitReasonForDebugging::Arbitration);
@ -359,7 +335,7 @@ ResultCode KAddressArbiter::WaitIfEqual(VAddr addr, s32 value, s64 timeout) {
// Get the result. // Get the result.
KSynchronizationObject* dummy{}; KSynchronizationObject* dummy{};
return cur_thread->GetWaitResult(std::addressof(dummy)); return cur_thread->GetWaitResult(&dummy);
} }
} // namespace Kernel } // namespace Kernel