Compare commits

...

13 Commits

Author SHA1 Message Date
ReinUsesLisp
d9a15a935b vulkan_device: Remove requirement on shaderStorageImageMultisample
yuzu doesn't currently emulate MS image stores. Requiring this makes no
sense for now. Fixes ANV not booting any games on Vulkan.
2021-01-13 06:21:33 -03:00
LC
c320da3f63 Merge pull request #5340 from Morph1984/gcc-warnings
cmake: Enforce -Werror=switch and -Werror=unused-variable
2021-01-13 02:30:31 -05:00
Morph
2b98da2ed4 cmake: Enforce -Werror=switch and -Werror=unused-variable 2021-01-13 01:57:18 -05:00
bunnei
0fb19e9bef Merge pull request #5280 from FearlessTobi/port-5666
Port citra-emu/citra#5666: "Rotate previous log file to "citra_log.txt.old""
2021-01-12 22:16:57 -08:00
bunnei
de1a316369 Merge pull request #5311 from ReinUsesLisp/fence-wait
vk_fence_manager: Use timeline semaphores instead of spin waits
2021-01-12 21:00:05 -08:00
bunnei
99d2d77062 Merge pull request #5333 from lioncash/define
common/parent_of_member: Replace TYPED_STORAGE define with template alias
2021-01-11 20:47:30 -08:00
Lioncash
703c57a119 common/parent_of_member: Replace TYPED_STORAGE define with template alias
Provides the same construct, but makes it obey namespacing.
2021-01-11 18:26:04 -05:00
bunnei
eb3cb54aa5 Merge pull request #5266 from bunnei/kernel-synch
Rewrite KSynchronizationObject, KConditonVariable, and KAddressArbiter
2021-01-11 14:36:26 -08:00
ReinUsesLisp
154a7653f9 vk_fence_manager: Use timeline semaphores instead of spin waits
With timeline semaphores we can avoid creating objects. Instead of
creating an event, grab the current tick from the scheduler and flush
the current command buffer. When the fence has to be queried/waited, we
can do so against the master semaphore instead of spinning on an event.

If Vulkan supported NVN like events or fences, we could signal from the
command buffer and wait for that without splitting things in two
separate command buffers.
2021-01-08 02:47:28 -03:00
FearlessTobi
beb951770a Address review comments 2021-01-04 04:36:50 +01:00
xperia64
fd5776aac2 Delete the old log file before rotating (#5675) 2021-01-04 04:33:34 +01:00
bunnei
bf8bd60ab3 Fix the old log file to work with the log parser. 2021-01-03 01:44:52 +01:00
xperia64
f478a57737 Rotate previous log file to '.old' if it exists 2021-01-03 01:44:42 +01:00
8 changed files with 43 additions and 68 deletions

View File

@@ -67,8 +67,10 @@ else()
-Werror=implicit-fallthrough
-Werror=missing-declarations
-Werror=reorder
-Werror=switch
-Werror=uninitialized
-Werror=unused-result
-Werror=unused-variable
-Wextra
-Wmissing-declarations
-Wno-attributes

View File

@@ -533,7 +533,7 @@ private:
}
private:
static constexpr TYPED_STORAGE(Derived) DerivedStorage = {};
static constexpr TypedStorage<Derived> DerivedStorage = {};
static_assert(GetParent(GetNode(GetPointer(DerivedStorage))) == GetPointer(DerivedStorage));
};
@@ -549,7 +549,7 @@ public:
using TreeTypeImpl = impl::IntrusiveRedBlackTreeImpl;
static constexpr bool IsValid() {
TYPED_STORAGE(Derived) DerivedStorage = {};
TypedStorage<Derived> DerivedStorage = {};
return GetParent(GetNode(GetPointer(DerivedStorage))) == GetPointer(DerivedStorage);
}

View File

@@ -145,10 +145,18 @@ void ColorConsoleBackend::Write(const Entry& entry) {
PrintColoredMessage(entry);
}
// _SH_DENYWR allows read only access to the file for other programs.
// It is #defined to 0 on other platforms
FileBackend::FileBackend(const std::string& filename)
: file(filename, "w", _SH_DENYWR), bytes_written(0) {}
FileBackend::FileBackend(const std::string& filename) : bytes_written(0) {
if (Common::FS::Exists(filename + ".old.txt")) {
Common::FS::Delete(filename + ".old.txt");
}
if (Common::FS::Exists(filename)) {
Common::FS::Rename(filename, filename + ".old.txt");
}
// _SH_DENYWR allows read only access to the file for other programs.
// It is #defined to 0 on other platforms
file = Common::FS::IOFile(filename, "w", _SH_DENYWR);
}
void FileBackend::Write(const Entry& entry) {
// prevent logs from going over the maximum size (in case its spamming and the user doesn't

View File

@@ -10,21 +10,23 @@
#include "common/common_types.h"
namespace Common {
namespace detail {
template <typename T, size_t Size, size_t Align>
struct TypedStorage {
struct TypedStorageImpl {
std::aligned_storage_t<Size, Align> storage_;
};
#define TYPED_STORAGE(...) TypedStorage<__VA_ARGS__, sizeof(__VA_ARGS__), alignof(__VA_ARGS__)>
} // namespace detail
template <typename T>
static constexpr T* GetPointer(TYPED_STORAGE(T) & ts) {
using TypedStorage = detail::TypedStorageImpl<T, sizeof(T), alignof(T)>;
template <typename T>
static constexpr T* GetPointer(TypedStorage<T>& ts) {
return static_cast<T*>(static_cast<void*>(std::addressof(ts.storage_)));
}
template <typename T>
static constexpr const T* GetPointer(const TYPED_STORAGE(T) & ts) {
static constexpr const T* GetPointer(const TypedStorage<T>& ts) {
return static_cast<const T*>(static_cast<const void*>(std::addressof(ts.storage_)));
}
@@ -72,7 +74,7 @@ struct OffsetOfCalculator {
union Union {
char c{};
UnionHolder first_union;
TYPED_STORAGE(ParentType) parent;
TypedStorage<ParentType> parent;
constexpr Union() : c() {}
};

View File

@@ -3,7 +3,6 @@
// Refer to the license.txt file included.
#include <memory>
#include <thread>
#include "video_core/renderer_vulkan/vk_buffer_cache.h"
#include "video_core/renderer_vulkan/vk_fence_manager.h"
@@ -14,13 +13,11 @@
namespace Vulkan {
InnerFence::InnerFence(const Device& device_, VKScheduler& scheduler_, u32 payload_,
bool is_stubbed_)
: FenceBase{payload_, is_stubbed_}, device{device_}, scheduler{scheduler_} {}
InnerFence::InnerFence(VKScheduler& scheduler_, u32 payload_, bool is_stubbed_)
: FenceBase{payload_, is_stubbed_}, scheduler{scheduler_} {}
InnerFence::InnerFence(const Device& device_, VKScheduler& scheduler_, GPUVAddr address_,
u32 payload_, bool is_stubbed_)
: FenceBase{address_, payload_, is_stubbed_}, device{device_}, scheduler{scheduler_} {}
InnerFence::InnerFence(VKScheduler& scheduler_, GPUVAddr address_, u32 payload_, bool is_stubbed_)
: FenceBase{address_, payload_, is_stubbed_}, scheduler{scheduler_} {}
InnerFence::~InnerFence() = default;
@@ -28,63 +25,38 @@ void InnerFence::Queue() {
if (is_stubbed) {
return;
}
ASSERT(!event);
event = device.GetLogical().CreateEvent();
ticks = scheduler.CurrentTick();
scheduler.RequestOutsideRenderPassOperationContext();
scheduler.Record([event = *event](vk::CommandBuffer cmdbuf) {
cmdbuf.SetEvent(event, VK_PIPELINE_STAGE_ALL_COMMANDS_BIT);
});
// Get the current tick so we can wait for it
wait_tick = scheduler.CurrentTick();
scheduler.Flush();
}
bool InnerFence::IsSignaled() const {
if (is_stubbed) {
return true;
}
ASSERT(event);
return IsEventSignalled();
return scheduler.IsFree(wait_tick);
}
void InnerFence::Wait() {
if (is_stubbed) {
return;
}
ASSERT(event);
if (ticks >= scheduler.CurrentTick()) {
scheduler.Flush();
}
while (!IsEventSignalled()) {
std::this_thread::yield();
}
}
bool InnerFence::IsEventSignalled() const {
switch (const VkResult result = event.GetStatus()) {
case VK_EVENT_SET:
return true;
case VK_EVENT_RESET:
return false;
default:
throw vk::Exception(result);
}
scheduler.Wait(wait_tick);
}
VKFenceManager::VKFenceManager(VideoCore::RasterizerInterface& rasterizer_, Tegra::GPU& gpu_,
Tegra::MemoryManager& memory_manager_, TextureCache& texture_cache_,
VKBufferCache& buffer_cache_, VKQueryCache& query_cache_,
const Device& device_, VKScheduler& scheduler_)
VKScheduler& scheduler_)
: GenericFenceManager{rasterizer_, gpu_, texture_cache_, buffer_cache_, query_cache_},
device{device_}, scheduler{scheduler_} {}
scheduler{scheduler_} {}
Fence VKFenceManager::CreateFence(u32 value, bool is_stubbed) {
return std::make_shared<InnerFence>(device, scheduler, value, is_stubbed);
return std::make_shared<InnerFence>(scheduler, value, is_stubbed);
}
Fence VKFenceManager::CreateFence(GPUVAddr addr, u32 value, bool is_stubbed) {
return std::make_shared<InnerFence>(device, scheduler, addr, value, is_stubbed);
return std::make_shared<InnerFence>(scheduler, addr, value, is_stubbed);
}
void VKFenceManager::QueueFence(Fence& fence) {

View File

@@ -28,10 +28,8 @@ class VKScheduler;
class InnerFence : public VideoCommon::FenceBase {
public:
explicit InnerFence(const Device& device_, VKScheduler& scheduler_, u32 payload_,
bool is_stubbed_);
explicit InnerFence(const Device& device_, VKScheduler& scheduler_, GPUVAddr address_,
u32 payload_, bool is_stubbed_);
explicit InnerFence(VKScheduler& scheduler_, u32 payload_, bool is_stubbed_);
explicit InnerFence(VKScheduler& scheduler_, GPUVAddr address_, u32 payload_, bool is_stubbed_);
~InnerFence();
void Queue();
@@ -41,12 +39,8 @@ public:
void Wait();
private:
bool IsEventSignalled() const;
const Device& device;
VKScheduler& scheduler;
vk::Event event;
u64 ticks = 0;
u64 wait_tick = 0;
};
using Fence = std::shared_ptr<InnerFence>;
@@ -58,7 +52,7 @@ public:
explicit VKFenceManager(VideoCore::RasterizerInterface& rasterizer_, Tegra::GPU& gpu_,
Tegra::MemoryManager& memory_manager_, TextureCache& texture_cache_,
VKBufferCache& buffer_cache_, VKQueryCache& query_cache_,
const Device& device_, VKScheduler& scheduler_);
VKScheduler& scheduler_);
protected:
Fence CreateFence(u32 value, bool is_stubbed) override;
@@ -68,7 +62,6 @@ protected:
void WaitFence(Fence& fence) override;
private:
const Device& device;
VKScheduler& scheduler;
};

View File

@@ -428,8 +428,7 @@ RasterizerVulkan::RasterizerVulkan(Core::Frontend::EmuWindow& emu_window_, Tegra
buffer_cache(*this, gpu_memory, cpu_memory_, device, memory_manager, scheduler, stream_buffer,
staging_pool),
query_cache{*this, maxwell3d, gpu_memory, device, scheduler},
fence_manager(*this, gpu, gpu_memory, texture_cache, buffer_cache, query_cache, device,
scheduler),
fence_manager(*this, gpu, gpu_memory, texture_cache, buffer_cache, query_cache, scheduler),
wfi_event(device.GetLogical().CreateEvent()), async_shaders(emu_window_) {
scheduler.SetQueryCache(query_cache);
if (device.UseAsynchronousShaders()) {

View File

@@ -604,7 +604,6 @@ void Device::CheckSuitability() const {
std::make_pair(features.occlusionQueryPrecise, "occlusionQueryPrecise"),
std::make_pair(features.fragmentStoresAndAtomics, "fragmentStoresAndAtomics"),
std::make_pair(features.shaderImageGatherExtended, "shaderImageGatherExtended"),
std::make_pair(features.shaderStorageImageMultisample, "shaderStorageImageMultisample"),
std::make_pair(features.shaderStorageImageWriteWithoutFormat,
"shaderStorageImageWriteWithoutFormat"),
};