diff options
| author | 2015-01-14 10:04:33 -0500 | |
|---|---|---|
| committer | 2015-01-14 10:04:33 -0500 | |
| commit | 394d44cf7480da210f5aeac9c0d86462b0c36d57 (patch) | |
| tree | 47c2fee9bbf771240c3b2b34505a9710a9b421b8 /src | |
| parent | Merge pull request #473 from archshift/pp3ports (diff) | |
| parent | AddrArbiter: Implement arbitration types 3 and 4. (diff) | |
| download | yuzu-394d44cf7480da210f5aeac9c0d86462b0c36d57.tar.gz yuzu-394d44cf7480da210f5aeac9c0d86462b0c36d57.tar.xz yuzu-394d44cf7480da210f5aeac9c0d86462b0c36d57.zip | |
Merge pull request #480 from Subv/arb_2
AddrArbiter: Implement arbitration types 3 and 4.
Diffstat (limited to 'src')
| -rw-r--r-- | src/core/hle/kernel/address_arbiter.cpp | 21 | ||||
| -rw-r--r-- | src/core/hle/kernel/address_arbiter.h | 2 | ||||
| -rw-r--r-- | src/core/hle/svc.cpp | 2 |
3 files changed, 21 insertions, 4 deletions
diff --git a/src/core/hle/kernel/address_arbiter.cpp b/src/core/hle/kernel/address_arbiter.cpp index 62e3460e1..b7434aaf2 100644 --- a/src/core/hle/kernel/address_arbiter.cpp +++ b/src/core/hle/kernel/address_arbiter.cpp | |||
| @@ -29,7 +29,7 @@ public: | |||
| 29 | //////////////////////////////////////////////////////////////////////////////////////////////////// | 29 | //////////////////////////////////////////////////////////////////////////////////////////////////// |
| 30 | 30 | ||
| 31 | /// Arbitrate an address | 31 | /// Arbitrate an address |
| 32 | ResultCode ArbitrateAddress(Handle handle, ArbitrationType type, u32 address, s32 value) { | 32 | ResultCode ArbitrateAddress(Handle handle, ArbitrationType type, u32 address, s32 value, u64 nanoseconds) { |
| 33 | Object* object = Kernel::g_handle_table.GetGeneric(handle).get(); | 33 | Object* object = Kernel::g_handle_table.GetGeneric(handle).get(); |
| 34 | if (object == nullptr) | 34 | if (object == nullptr) |
| 35 | return InvalidHandle(ErrorModule::Kernel); | 35 | return InvalidHandle(ErrorModule::Kernel); |
| @@ -55,7 +55,13 @@ ResultCode ArbitrateAddress(Handle handle, ArbitrationType type, u32 address, s3 | |||
| 55 | HLE::Reschedule(__func__); | 55 | HLE::Reschedule(__func__); |
| 56 | } | 56 | } |
| 57 | break; | 57 | break; |
| 58 | 58 | case ArbitrationType::WaitIfLessThanWithTimeout: | |
| 59 | if ((s32)Memory::Read32(address) <= value) { | ||
| 60 | Kernel::WaitCurrentThread(WAITTYPE_ARB, object, address); | ||
| 61 | Kernel::WakeThreadAfterDelay(GetCurrentThread(), nanoseconds); | ||
| 62 | HLE::Reschedule(__func__); | ||
| 63 | } | ||
| 64 | break; | ||
| 59 | case ArbitrationType::DecrementAndWaitIfLessThan: | 65 | case ArbitrationType::DecrementAndWaitIfLessThan: |
| 60 | { | 66 | { |
| 61 | s32 memory_value = Memory::Read32(address) - 1; | 67 | s32 memory_value = Memory::Read32(address) - 1; |
| @@ -66,6 +72,17 @@ ResultCode ArbitrateAddress(Handle handle, ArbitrationType type, u32 address, s3 | |||
| 66 | } | 72 | } |
| 67 | break; | 73 | break; |
| 68 | } | 74 | } |
| 75 | case ArbitrationType::DecrementAndWaitIfLessThanWithTimeout: | ||
| 76 | { | ||
| 77 | s32 memory_value = Memory::Read32(address) - 1; | ||
| 78 | Memory::Write32(address, memory_value); | ||
| 79 | if (memory_value <= value) { | ||
| 80 | Kernel::WaitCurrentThread(WAITTYPE_ARB, object, address); | ||
| 81 | Kernel::WakeThreadAfterDelay(GetCurrentThread(), nanoseconds); | ||
| 82 | HLE::Reschedule(__func__); | ||
| 83 | } | ||
| 84 | break; | ||
| 85 | } | ||
| 69 | 86 | ||
| 70 | default: | 87 | default: |
| 71 | LOG_ERROR(Kernel, "unknown type=%d", type); | 88 | LOG_ERROR(Kernel, "unknown type=%d", type); |
diff --git a/src/core/hle/kernel/address_arbiter.h b/src/core/hle/kernel/address_arbiter.h index 030e7ad7b..3ffd465a2 100644 --- a/src/core/hle/kernel/address_arbiter.h +++ b/src/core/hle/kernel/address_arbiter.h | |||
| @@ -28,7 +28,7 @@ enum class ArbitrationType : u32 { | |||
| 28 | }; | 28 | }; |
| 29 | 29 | ||
| 30 | /// Arbitrate an address | 30 | /// Arbitrate an address |
| 31 | ResultCode ArbitrateAddress(Handle handle, ArbitrationType type, u32 address, s32 value); | 31 | ResultCode ArbitrateAddress(Handle handle, ArbitrationType type, u32 address, s32 value, u64 nanoseconds); |
| 32 | 32 | ||
| 33 | /// Create an address arbiter | 33 | /// Create an address arbiter |
| 34 | Handle CreateAddressArbiter(const std::string& name = "Unknown"); | 34 | Handle CreateAddressArbiter(const std::string& name = "Unknown"); |
diff --git a/src/core/hle/svc.cpp b/src/core/hle/svc.cpp index 5c6a3be80..a487f757c 100644 --- a/src/core/hle/svc.cpp +++ b/src/core/hle/svc.cpp | |||
| @@ -194,7 +194,7 @@ static Result ArbitrateAddress(Handle arbiter, u32 address, u32 type, u32 value, | |||
| 194 | LOG_TRACE(Kernel_SVC, "called handle=0x%08X, address=0x%08X, type=0x%08X, value=0x%08X", arbiter, | 194 | LOG_TRACE(Kernel_SVC, "called handle=0x%08X, address=0x%08X, type=0x%08X, value=0x%08X", arbiter, |
| 195 | address, type, value); | 195 | address, type, value); |
| 196 | return Kernel::ArbitrateAddress(arbiter, static_cast<Kernel::ArbitrationType>(type), | 196 | return Kernel::ArbitrateAddress(arbiter, static_cast<Kernel::ArbitrationType>(type), |
| 197 | address, value).raw; | 197 | address, value, nanoseconds).raw; |
| 198 | } | 198 | } |
| 199 | 199 | ||
| 200 | /// Used to output a message on a debug hardware unit - does nothing on a retail unit | 200 | /// Used to output a message on a debug hardware unit - does nothing on a retail unit |