diff --git a/OptiScaler/framegen/IFGFeature_Dx12.cpp b/OptiScaler/framegen/IFGFeature_Dx12.cpp index ec2ce43f..5b499634 100644 --- a/OptiScaler/framegen/IFGFeature_Dx12.cpp +++ b/OptiScaler/framegen/IFGFeature_Dx12.cpp @@ -302,6 +302,9 @@ bool IFGFeature_Dx12::CreateBufferResource(ID3D12Device* device, ID3D12Resource* void IFGFeature_Dx12::ResourceBarrier(ID3D12GraphicsCommandList* cmdList, ID3D12Resource* resource, D3D12_RESOURCE_STATES beforeState, D3D12_RESOURCE_STATES afterState) { + if (beforeState == afterState) + return; + D3D12_RESOURCE_BARRIER barrier = {}; barrier.Type = D3D12_RESOURCE_BARRIER_TYPE_TRANSITION; barrier.Transition.pResource = resource; diff --git a/OptiScaler/framegen/xefg/XeFG_Dx12.cpp b/OptiScaler/framegen/xefg/XeFG_Dx12.cpp index 3c4da211..854e540e 100644 --- a/OptiScaler/framegen/xefg/XeFG_Dx12.cpp +++ b/OptiScaler/framegen/xefg/XeFG_Dx12.cpp @@ -878,6 +878,15 @@ void XeFG_Dx12::SetResource(Dx12Resource* inputResource) if (fResource->cmdList == nullptr && resourceParam.validity == XEFG_SWAPCHAIN_RV_UNTIL_NEXT_PRESENT) fResource->cmdList = (ID3D12GraphicsCommandList*) 1; + // HACK: XeFG seems to crash if the resource is in COPY_SOURCE state + // even though the docs say it's the preferred state + if (inputResource->state == D3D12_RESOURCE_STATE_COPY_SOURCE) + { + ResourceBarrier(inputResource->cmdList, inputResource->resource, inputResource->state, + D3D12_RESOURCE_STATE_COPY_DEST); + resourceParam.incomingState = D3D12_RESOURCE_STATE_COPY_DEST; + } + auto result = XeFGProxy::D3D12TagFrameResource()(_swapChainContext, fResource->cmdList, _frameCount, &resourceParam); if (result != XEFG_SWAPCHAIN_RESULT_SUCCESS) @@ -887,6 +896,13 @@ void XeFG_Dx12::SetResource(Dx12Resource* inputResource) return; } + // Potentially we don't need to restore but do it just to be safe + if (inputResource->state == D3D12_RESOURCE_STATE_COPY_SOURCE) + { + ResourceBarrier(inputResource->cmdList, inputResource->resource, D3D12_RESOURCE_STATE_COPY_DEST, + inputResource->state); + } + SetResourceReady(type); LOG_TRACE("_frameResources[{}][{}]: {:X}", fIndex, magic_enum::enum_name(type), (size_t) fResource->GetResource()); diff --git a/OptiScaler/hudfix/Hudfix_Dx12.cpp b/OptiScaler/hudfix/Hudfix_Dx12.cpp index ffd914df..1b933283 100644 --- a/OptiScaler/hudfix/Hudfix_Dx12.cpp +++ b/OptiScaler/hudfix/Hudfix_Dx12.cpp @@ -179,6 +179,9 @@ bool Hudfix_Dx12::CreateBufferResourceWithSize(ID3D12Device* InDevice, ResourceI void Hudfix_Dx12::ResourceBarrier(ID3D12GraphicsCommandList* InCommandList, ID3D12Resource* InResource, D3D12_RESOURCE_STATES InBeforeState, D3D12_RESOURCE_STATES InAfterState) { + if (InBeforeState == InAfterState) + return; + D3D12_RESOURCE_BARRIER barrier = {}; barrier.Type = D3D12_RESOURCE_BARRIER_TYPE_TRANSITION; barrier.Transition.pResource = InResource; diff --git a/OptiScaler/inputs/FG/FfxApi_Dx12_FG.cpp b/OptiScaler/inputs/FG/FfxApi_Dx12_FG.cpp index a9edfb6e..3d7767fc 100644 --- a/OptiScaler/inputs/FG/FfxApi_Dx12_FG.cpp +++ b/OptiScaler/inputs/FG/FfxApi_Dx12_FG.cpp @@ -136,6 +136,9 @@ static bool CreateBufferResource(ID3D12Device* InDevice, ID3D12Resource* InResou static void ResourceBarrier(ID3D12GraphicsCommandList* InCommandList, ID3D12Resource* InResource, D3D12_RESOURCE_STATES InBeforeState, D3D12_RESOURCE_STATES InAfterState) { + if (InBeforeState == InAfterState) + return; + D3D12_RESOURCE_BARRIER barrier = {}; barrier.Type = D3D12_RESOURCE_BARRIER_TYPE_TRANSITION; barrier.Transition.pResource = InResource; diff --git a/OptiScaler/shaders/hudless_compare/HC_Dx12.cpp b/OptiScaler/shaders/hudless_compare/HC_Dx12.cpp index ea8b6e10..84aaca72 100644 --- a/OptiScaler/shaders/hudless_compare/HC_Dx12.cpp +++ b/OptiScaler/shaders/hudless_compare/HC_Dx12.cpp @@ -100,6 +100,9 @@ bool HC_Dx12::CreateBufferResource(UINT index, ID3D12Device* InDevice, ID3D12Res void HC_Dx12::ResourceBarrier(ID3D12GraphicsCommandList* cmdList, ID3D12Resource* resource, D3D12_RESOURCE_STATES beforeState, D3D12_RESOURCE_STATES afterState) { + if (beforeState == afterState) + return; + D3D12_RESOURCE_BARRIER barrier = {}; barrier.Type = D3D12_RESOURCE_BARRIER_TYPE_TRANSITION; barrier.Transition.pResource = resource; diff --git a/OptiScaler/upscalers/IFeature_Dx11wDx12.cpp b/OptiScaler/upscalers/IFeature_Dx11wDx12.cpp index 3384a71c..1a1c1084 100644 --- a/OptiScaler/upscalers/IFeature_Dx11wDx12.cpp +++ b/OptiScaler/upscalers/IFeature_Dx11wDx12.cpp @@ -22,6 +22,9 @@ void IFeature_Dx11wDx12::ResourceBarrier(ID3D12GraphicsCommandList* commandList, ID3D12Resource* resource, D3D12_RESOURCE_STATES beforeState, D3D12_RESOURCE_STATES afterState) { + if (beforeState == afterState) + return; + D3D12_RESOURCE_BARRIER barrier = {}; barrier.Type = D3D12_RESOURCE_BARRIER_TYPE_TRANSITION; barrier.Transition.pResource = resource; diff --git a/OptiScaler/upscalers/IFeature_Dx12.cpp b/OptiScaler/upscalers/IFeature_Dx12.cpp index 8ea7e3dc..8bd59770 100644 --- a/OptiScaler/upscalers/IFeature_Dx12.cpp +++ b/OptiScaler/upscalers/IFeature_Dx12.cpp @@ -6,6 +6,9 @@ void IFeature_Dx12::ResourceBarrier(ID3D12GraphicsCommandList* InCommandList, ID3D12Resource* InResource, D3D12_RESOURCE_STATES InBeforeState, D3D12_RESOURCE_STATES InAfterState) const { + if (InBeforeState == InAfterState) + return; + D3D12_RESOURCE_BARRIER barrier = {}; barrier.Type = D3D12_RESOURCE_BARRIER_TYPE_TRANSITION; barrier.Transition.pResource = InResource;