diff --git a/WickedEngine/wiGraphicsDevice_DX12.cpp b/WickedEngine/wiGraphicsDevice_DX12.cpp index 033a91409..ff0847caa 100644 --- a/WickedEngine/wiGraphicsDevice_DX12.cpp +++ b/WickedEngine/wiGraphicsDevice_DX12.cpp @@ -1732,20 +1732,18 @@ using namespace dx12_internal; const uint64_t wrapped_offset_end = wrapped_offset + stats.descriptorCopyCount; // Check that gpu offset doesn't intersect with our newly allocated range, if it does, we need to wait until gpu finishes with it: + // First check is with the cached completed value to avoid API call into fence object uint64_t wrapped_gpu_offset = heap.cached_completedValue % wrap_effective_size; - int loop_cnt = 0; // safety - while (wrapped_offset < wrapped_gpu_offset && wrapped_gpu_offset <= wrapped_offset_end) + if ((wrapped_offset < wrapped_gpu_offset) && (wrapped_gpu_offset < wrapped_offset_end)) { - wrapped_gpu_offset = device->descriptorheap_res.fence->GetCompletedValue() % wrap_effective_size; - - // Check that the GPU has even a chance of freeing up the requested descriptors: - const uint64_t wrapped_signaled_offset = heap.fenceValue % wrap_effective_size; - if (wrapped_signaled_offset <= wrapped_offset_end || loop_cnt > 10) + // Second check is with current fence value with API call: + wrapped_gpu_offset = heap.fence->GetCompletedValue() % wrap_effective_size; + if ((wrapped_offset < wrapped_gpu_offset) && (wrapped_gpu_offset < wrapped_offset_end)) { - assert(0); - break; // break out from waiting for GPU, because it might cause infinite loop + // Third step is actual wait until GPU updates fence so that requested descriptors are free: + HRESULT hr = heap.fence->SetEventOnCompletion(heap.fenceValue, nullptr); + assert(SUCCEEDED(hr)); } - loop_cnt++; } gpu_handle.ptr += (size_t)ringoffset; diff --git a/WickedEngine/wiHelper.cpp b/WickedEngine/wiHelper.cpp index dd5553725..fd8880e01 100644 --- a/WickedEngine/wiHelper.cpp +++ b/WickedEngine/wiHelper.cpp @@ -732,8 +732,53 @@ namespace wi::helper bool FileExists(const std::string& fileName) { +#ifndef PLATFORM_UWP bool exists = std::filesystem::exists(fileName); return exists; +#else + using namespace winrt::Windows::Storage; + using namespace winrt::Windows::Storage::Streams; + using namespace winrt::Windows::Foundation; + std::wstring wstr; + std::filesystem::path filepath = fileName; + filepath = std::filesystem::absolute(filepath); + StringConvert(filepath.string(), wstr); + bool success = false; + + auto async_helper = [&]() -> IAsyncAction { + try + { + auto file = co_await StorageFile::GetFileFromPathAsync(wstr); + success = true; + } + catch (winrt::hresult_error const& ex) + { + switch (ex.code()) + { + case E_ACCESSDENIED: + wi::backlog::post("Opening file failed: " + fileName + " | Reason: Permission Denied!"); + break; + default: + break; + } + } + + }; + + if (winrt::impl::is_sta_thread()) + { + std::thread([&] { async_helper().get(); }).join(); // can't block coroutine from ui thread + } + else + { + async_helper().get(); + } + + if (success) + { + return true; + } +#endif // PLATFORM_UWP } std::string GetTempDirectoryPath()