diff options
| author | 2023-08-19 21:49:38 +0200 | |
|---|---|---|
| committer | 2023-09-23 23:05:30 +0200 | |
| commit | 2fea1b8407b66dd0e9ed1776c34dad043e1becf4 (patch) | |
| tree | 4a5ad2bc67d2f07c1fafd7d3d1afb8d8b473fb9a /src/video_core/query_cache | |
| parent | Query Cache: address issues (diff) | |
| download | yuzu-2fea1b8407b66dd0e9ed1776c34dad043e1becf4.tar.gz yuzu-2fea1b8407b66dd0e9ed1776c34dad043e1becf4.tar.xz yuzu-2fea1b8407b66dd0e9ed1776c34dad043e1becf4.zip | |
Query Cache: Fix guest side sample counting
Diffstat (limited to 'src/video_core/query_cache')
| -rw-r--r-- | src/video_core/query_cache/query_base.h | 19 | ||||
| -rw-r--r-- | src/video_core/query_cache/query_cache.h | 46 | ||||
| -rw-r--r-- | src/video_core/query_cache/query_stream.h | 10 |
3 files changed, 43 insertions, 32 deletions
diff --git a/src/video_core/query_cache/query_base.h b/src/video_core/query_cache/query_base.h index 993a13eac..1d786b3a7 100644 --- a/src/video_core/query_cache/query_base.h +++ b/src/video_core/query_cache/query_base.h | |||
| @@ -9,16 +9,15 @@ | |||
| 9 | namespace VideoCommon { | 9 | namespace VideoCommon { |
| 10 | 10 | ||
| 11 | enum class QueryFlagBits : u32 { | 11 | enum class QueryFlagBits : u32 { |
| 12 | HasTimestamp = 1 << 0, ///< Indicates if this query has a timestamp. | 12 | HasTimestamp = 1 << 0, ///< Indicates if this query has a timestamp. |
| 13 | IsFinalValueSynced = 1 << 1, ///< Indicates if the query has been synced in the host | 13 | IsFinalValueSynced = 1 << 1, ///< Indicates if the query has been synced in the host |
| 14 | IsHostSynced = 1 << 2, ///< Indicates if the query has been synced in the host | 14 | IsHostSynced = 1 << 2, ///< Indicates if the query has been synced in the host |
| 15 | IsGuestSynced = 1 << 3, ///< Indicates if the query has been synced with the guest. | 15 | IsGuestSynced = 1 << 3, ///< Indicates if the query has been synced with the guest. |
| 16 | IsHostManaged = 1 << 4, ///< Indicates if this query points to a host query | 16 | IsHostManaged = 1 << 4, ///< Indicates if this query points to a host query |
| 17 | IsRewritten = 1 << 5, ///< Indicates if this query was rewritten by another query | 17 | IsRewritten = 1 << 5, ///< Indicates if this query was rewritten by another query |
| 18 | IsInvalidated = 1 << 6, ///< Indicates the value of th query has been nullified. | 18 | IsInvalidated = 1 << 6, ///< Indicates the value of th query has been nullified. |
| 19 | IsOrphan = 1 << 7, ///< Indicates the query has not been set by a guest query. | 19 | IsOrphan = 1 << 7, ///< Indicates the query has not been set by a guest query. |
| 20 | IsFence = 1 << 8, ///< Indicates the query is a fence. | 20 | IsFence = 1 << 8, ///< Indicates the query is a fence. |
| 21 | IsQueuedForAsyncFlush = 1 << 9, ///< Indicates that the query can be flushed at any moment | ||
| 22 | }; | 21 | }; |
| 23 | DECLARE_ENUM_FLAG_OPERATORS(QueryFlagBits) | 22 | DECLARE_ENUM_FLAG_OPERATORS(QueryFlagBits) |
| 24 | 23 | ||
diff --git a/src/video_core/query_cache/query_cache.h b/src/video_core/query_cache/query_cache.h index 042af053c..4b89b5bf6 100644 --- a/src/video_core/query_cache/query_cache.h +++ b/src/video_core/query_cache/query_cache.h | |||
| @@ -256,30 +256,32 @@ void QueryCacheBase<Traits>::CounterReport(GPUVAddr addr, QueryType counter_type | |||
| 256 | u8* pointer = impl->cpu_memory.GetPointer(cpu_addr); | 256 | u8* pointer = impl->cpu_memory.GetPointer(cpu_addr); |
| 257 | u8* pointer_timestamp = impl->cpu_memory.GetPointer(cpu_addr + 8); | 257 | u8* pointer_timestamp = impl->cpu_memory.GetPointer(cpu_addr + 8); |
| 258 | bool is_synced = !Settings::IsGPULevelHigh() && is_fence; | 258 | bool is_synced = !Settings::IsGPULevelHigh() && is_fence; |
| 259 | std::function<void()> operation( | 259 | std::function<void()> operation([this, is_synced, streamer, query_base = query, query_location, |
| 260 | [this, is_synced, query_base = query, query_location, pointer, pointer_timestamp] { | 260 | pointer, pointer_timestamp] { |
| 261 | if (True(query_base->flags & QueryFlagBits::IsInvalidated)) { | 261 | if (True(query_base->flags & QueryFlagBits::IsInvalidated)) { |
| 262 | if (!is_synced) [[likely]] { | ||
| 263 | impl->pending_unregister.push_back(query_location); | ||
| 264 | } | ||
| 265 | return; | ||
| 266 | } | ||
| 267 | if (False(query_base->flags & QueryFlagBits::IsFinalValueSynced)) [[unlikely]] { | ||
| 268 | UNREACHABLE(); | ||
| 269 | return; | ||
| 270 | } | ||
| 271 | if (True(query_base->flags & QueryFlagBits::HasTimestamp)) { | ||
| 272 | u64 timestamp = impl->gpu.GetTicks(); | ||
| 273 | std::memcpy(pointer_timestamp, ×tamp, sizeof(timestamp)); | ||
| 274 | std::memcpy(pointer, &query_base->value, sizeof(query_base->value)); | ||
| 275 | } else { | ||
| 276 | u32 value = static_cast<u32>(query_base->value); | ||
| 277 | std::memcpy(pointer, &value, sizeof(value)); | ||
| 278 | } | ||
| 279 | if (!is_synced) [[likely]] { | 262 | if (!is_synced) [[likely]] { |
| 280 | impl->pending_unregister.push_back(query_location); | 263 | impl->pending_unregister.push_back(query_location); |
| 281 | } | 264 | } |
| 282 | }); | 265 | return; |
| 266 | } | ||
| 267 | if (False(query_base->flags & QueryFlagBits::IsFinalValueSynced)) [[unlikely]] { | ||
| 268 | UNREACHABLE(); | ||
| 269 | return; | ||
| 270 | } | ||
| 271 | query_base->value += streamer->GetAmmendValue(); | ||
| 272 | streamer->SetAccumulationValue(query_base->value); | ||
| 273 | if (True(query_base->flags & QueryFlagBits::HasTimestamp)) { | ||
| 274 | u64 timestamp = impl->gpu.GetTicks(); | ||
| 275 | std::memcpy(pointer_timestamp, ×tamp, sizeof(timestamp)); | ||
| 276 | std::memcpy(pointer, &query_base->value, sizeof(query_base->value)); | ||
| 277 | } else { | ||
| 278 | u32 value = static_cast<u32>(query_base->value); | ||
| 279 | std::memcpy(pointer, &value, sizeof(value)); | ||
| 280 | } | ||
| 281 | if (!is_synced) [[likely]] { | ||
| 282 | impl->pending_unregister.push_back(query_location); | ||
| 283 | } | ||
| 284 | }); | ||
| 283 | if (is_fence) { | 285 | if (is_fence) { |
| 284 | impl->rasterizer.SignalFence(std::move(operation)); | 286 | impl->rasterizer.SignalFence(std::move(operation)); |
| 285 | } else { | 287 | } else { |
| @@ -354,9 +356,9 @@ void QueryCacheBase<Traits>::NotifySegment(bool resume) { | |||
| 354 | if (resume) { | 356 | if (resume) { |
| 355 | impl->runtime.ResumeHostConditionalRendering(); | 357 | impl->runtime.ResumeHostConditionalRendering(); |
| 356 | } else { | 358 | } else { |
| 357 | impl->runtime.PauseHostConditionalRendering(); | ||
| 358 | CounterClose(VideoCommon::QueryType::ZPassPixelCount64); | 359 | CounterClose(VideoCommon::QueryType::ZPassPixelCount64); |
| 359 | CounterClose(VideoCommon::QueryType::StreamingByteCount); | 360 | CounterClose(VideoCommon::QueryType::StreamingByteCount); |
| 361 | impl->runtime.PauseHostConditionalRendering(); | ||
| 360 | } | 362 | } |
| 361 | } | 363 | } |
| 362 | 364 | ||
diff --git a/src/video_core/query_cache/query_stream.h b/src/video_core/query_cache/query_stream.h index e7aac955b..39da6ac07 100644 --- a/src/video_core/query_cache/query_stream.h +++ b/src/video_core/query_cache/query_stream.h | |||
| @@ -78,6 +78,14 @@ public: | |||
| 78 | return dependence_mask; | 78 | return dependence_mask; |
| 79 | } | 79 | } |
| 80 | 80 | ||
| 81 | u64 GetAmmendValue() const { | ||
| 82 | return ammend_value; | ||
| 83 | } | ||
| 84 | |||
| 85 | void SetAccumulationValue(u64 new_value) { | ||
| 86 | acumulation_value = new_value; | ||
| 87 | } | ||
| 88 | |||
| 81 | protected: | 89 | protected: |
| 82 | void MakeDependent(StreamerInterface* depend_on) { | 90 | void MakeDependent(StreamerInterface* depend_on) { |
| 83 | dependence_mask |= 1ULL << depend_on->id; | 91 | dependence_mask |= 1ULL << depend_on->id; |
| @@ -87,6 +95,8 @@ protected: | |||
| 87 | const size_t id; | 95 | const size_t id; |
| 88 | u64 dependence_mask; | 96 | u64 dependence_mask; |
| 89 | u64 dependent_mask; | 97 | u64 dependent_mask; |
| 98 | u64 ammend_value{}; | ||
| 99 | u64 acumulation_value{}; | ||
| 90 | }; | 100 | }; |
| 91 | 101 | ||
| 92 | template <typename QueryType> | 102 | template <typename QueryType> |