Fixed SRG compile issue with metal which leads to multiple gpu crashes inlucde ImGuiPass render crash (#6315)

Signed-off-by: Qing Tao <55564570+VickyAtAZ@users.noreply.github.com>
This commit is contained in:
Qing Tao
2021-12-10 09:53:02 -08:00
committed by GitHub
parent 63f8be12d5
commit 73f44684e8
2 changed files with 129 additions and 129 deletions
@@ -60,10 +60,19 @@ namespace AZ
NSError* error = nil;
id<MTLLibrary> lib = nil;
bool loadFromByteCode = false;
// MacOS Big Sur (11.16.x) has issue loading some shader's byte code when GPUCapture(Metal) is on.
// Only enable it for Monterey (12.x)
if(@available(iOS 14.0, macOS 12.0, *))
{
loadFromByteCode = true;
}
const uint8_t* shaderByteCode = reinterpret_cast<const uint8_t*>(shaderFunction->GetByteCode().data());
const int byteCodeLength = shaderFunction->GetByteCode().size();
if(byteCodeLength > 0 )
if(byteCodeLength > 0 && loadFromByteCode)
{
dispatch_data_t dispatchByteCodeData = dispatch_data_create(shaderByteCode, byteCodeLength, NULL, DISPATCH_DATA_DESTRUCTOR_DEFAULT);
lib = [mtlDevice newLibraryWithData:dispatchByteCodeData error:&error];
@@ -73,7 +82,7 @@ namespace AZ
//In case byte code was not generated try to create the lib with source code
MTLCompileOptions* compileOptions = [MTLCompileOptions alloc];
compileOptions.fastMathEnabled = YES;
compileOptions.languageVersion = MTLLanguageVersion2_0;
compileOptions.languageVersion = MTLLanguageVersion2_2;
lib = [mtlDevice newLibraryWithSource:source
options:compileOptions
error:&error];
@@ -1,126 +1,117 @@
/*
* Copyright (c) Contributors to the Open 3D Engine Project.
* For complete copyright and license terms please see the LICENSE at the root of this distribution.
*
* SPDX-License-Identifier: Apache-2.0 OR MIT
*
*/
#include <RHI/ArgumentBuffer.h>
#include <RHI/Conversions.h>
#include <RHI/Device.h>
#include <RHI/ShaderResourceGroup.h>
#include <RHI/ShaderResourceGroupPool.h>
namespace AZ
{
namespace Metal
{
RHI::Ptr<ShaderResourceGroupPool> ShaderResourceGroupPool::Create()
{
return aznew ShaderResourceGroupPool();
}
RHI::ResultCode ShaderResourceGroupPool::InitInternal(RHI::Device& deviceBase, const RHI::ShaderResourceGroupPoolDescriptor& descriptor)
{
Device& device = static_cast<Device&>(deviceBase);
m_device = &device;
m_srgLayout = descriptor.m_layout;
return RHI::ResultCode::Success;
}
void ShaderResourceGroupPool::ShutdownInternal()
{
Base::ShutdownInternal();
}
RHI::ResultCode ShaderResourceGroupPool::InitGroupInternal(RHI::ShaderResourceGroup& groupBase)
{
ShaderResourceGroup& group = static_cast<ShaderResourceGroup&>(groupBase);
for (size_t i = 0; i < RHI::Limits::Device::FrameCountMax; ++i)
{
auto argBuffer = ArgumentBuffer::Create();
argBuffer->Init(m_device, m_srgLayout, group, this);
group.m_compiledArgBuffers[i] = argBuffer;
}
return RHI::ResultCode::Success;
}
void ShaderResourceGroupPool::ShutdownResourceInternal(RHI::Resource& resourceBase)
{
ShaderResourceGroup& group = static_cast<ShaderResourceGroup&>(resourceBase);
for (size_t i = 0; i < RHI::Limits::Device::FrameCountMax; ++i)
{
group.m_compiledArgBuffers[i] = nullptr;
}
Base::ShutdownResourceInternal(resourceBase);
}
RHI::ResultCode ShaderResourceGroupPool::CompileGroupInternal(RHI::ShaderResourceGroup& groupBase, const RHI::ShaderResourceGroupData& groupData)
{
ShaderResourceGroup& group = static_cast<ShaderResourceGroup&>(groupBase);
group.UpdateCompiledDataIndex();
if (!groupData.IsAnyResourceTypeUpdated())
{
return RHI::ResultCode::Success;
}
ArgumentBuffer& argBuffer = *group.m_compiledArgBuffers[group.m_compiledDataIndex];
argBuffer.ClearResourceTracking();
auto constantData = groupData.GetConstantData();
if (!constantData.empty() && groupData.IsResourceTypeEnabledForCompilation(static_cast<uint32_t>(RHI::ShaderResourceGroupData::ResourceTypeMask::ConstantDataMask)))
{
argBuffer.UpdateConstantBufferViews(groupData.GetConstantData());
}
const RHI::ShaderResourceGroupLayout* layout = groupData.GetLayout();
uint32_t shaderInputIndex = 0;
if (groupData.IsResourceTypeEnabledForCompilation(static_cast<uint32_t>(RHI::ShaderResourceGroupData::ResourceTypeMask::ImageViewMask)))
{
for (const RHI::ShaderInputImageDescriptor& shaderInputImage : layout->GetShaderInputListForImages())
{
const RHI::ShaderInputImageIndex imageInputIndex(shaderInputIndex);
AZStd::array_view<RHI::ConstPtr<RHI::ImageView>> imageViews = groupData.GetImageViewArray(imageInputIndex);
argBuffer.UpdateImageViews(shaderInputImage, imageInputIndex, imageViews);
++shaderInputIndex;
}
}
if (groupData.IsResourceTypeEnabledForCompilation(static_cast<uint32_t>(RHI::ShaderResourceGroupData::ResourceTypeMask::SamplerMask)))
{
shaderInputIndex = 0;
for (const RHI::ShaderInputSamplerDescriptor& shaderInputSampler : layout->GetShaderInputListForSamplers())
{
const RHI::ShaderInputSamplerIndex samplerInputIndex(shaderInputIndex);
AZStd::array_view<RHI::SamplerState> samplerStates = groupData.GetSamplerArray(samplerInputIndex);
argBuffer.UpdateSamplers(shaderInputSampler, samplerInputIndex, samplerStates);
++shaderInputIndex;
}
}
if (groupData.IsResourceTypeEnabledForCompilation(static_cast<uint32_t>(RHI::ShaderResourceGroupData::ResourceTypeMask::BufferViewMask)))
{
shaderInputIndex = 0;
for (const RHI::ShaderInputBufferDescriptor& shaderInputBuffer : layout->GetShaderInputListForBuffers())
{
const RHI::ShaderInputBufferIndex bufferInputIndex(shaderInputIndex);
AZStd::array_view<RHI::ConstPtr<RHI::BufferView>> bufferViews = groupData.GetBufferViewArray(bufferInputIndex);
argBuffer.UpdateBufferViews(shaderInputBuffer, bufferInputIndex, bufferViews);
++shaderInputIndex;
}
}
return RHI::ResultCode::Success;
}
void ShaderResourceGroupPool::OnFrameEnd()
{
Base::OnFrameEnd();
}
}
}
/*
* Copyright (c) Contributors to the Open 3D Engine Project.
* For complete copyright and license terms please see the LICENSE at the root of this distribution.
*
* SPDX-License-Identifier: Apache-2.0 OR MIT
*
*/
#include <RHI/ArgumentBuffer.h>
#include <RHI/Conversions.h>
#include <RHI/Device.h>
#include <RHI/ShaderResourceGroup.h>
#include <RHI/ShaderResourceGroupPool.h>
namespace AZ
{
namespace Metal
{
RHI::Ptr<ShaderResourceGroupPool> ShaderResourceGroupPool::Create()
{
return aznew ShaderResourceGroupPool();
}
RHI::ResultCode ShaderResourceGroupPool::InitInternal(RHI::Device& deviceBase, const RHI::ShaderResourceGroupPoolDescriptor& descriptor)
{
Device& device = static_cast<Device&>(deviceBase);
m_device = &device;
m_srgLayout = descriptor.m_layout;
return RHI::ResultCode::Success;
}
void ShaderResourceGroupPool::ShutdownInternal()
{
Base::ShutdownInternal();
}
RHI::ResultCode ShaderResourceGroupPool::InitGroupInternal(RHI::ShaderResourceGroup& groupBase)
{
ShaderResourceGroup& group = static_cast<ShaderResourceGroup&>(groupBase);
for (size_t i = 0; i < RHI::Limits::Device::FrameCountMax; ++i)
{
auto argBuffer = ArgumentBuffer::Create();
argBuffer->Init(m_device, m_srgLayout, group, this);
group.m_compiledArgBuffers[i] = argBuffer;
}
return RHI::ResultCode::Success;
}
void ShaderResourceGroupPool::ShutdownResourceInternal(RHI::Resource& resourceBase)
{
ShaderResourceGroup& group = static_cast<ShaderResourceGroup&>(resourceBase);
for (size_t i = 0; i < RHI::Limits::Device::FrameCountMax; ++i)
{
group.m_compiledArgBuffers[i] = nullptr;
}
Base::ShutdownResourceInternal(resourceBase);
}
RHI::ResultCode ShaderResourceGroupPool::CompileGroupInternal(RHI::ShaderResourceGroup& groupBase, const RHI::ShaderResourceGroupData& groupData)
{
ShaderResourceGroup& group = static_cast<ShaderResourceGroup&>(groupBase);
if (!groupData.IsAnyResourceTypeUpdated())
{
return RHI::ResultCode::Success;
}
group.UpdateCompiledDataIndex();
ArgumentBuffer& argBuffer = *group.m_compiledArgBuffers[group.m_compiledDataIndex];
argBuffer.ClearResourceTracking();
auto constantData = groupData.GetConstantData();
if (!constantData.empty())
{
argBuffer.UpdateConstantBufferViews(groupData.GetConstantData());
}
const RHI::ShaderResourceGroupLayout* layout = groupData.GetLayout();
uint32_t shaderInputIndex = 0;
for (const RHI::ShaderInputImageDescriptor& shaderInputImage : layout->GetShaderInputListForImages())
{
const RHI::ShaderInputImageIndex imageInputIndex(shaderInputIndex);
AZStd::array_view<RHI::ConstPtr<RHI::ImageView>> imageViews = groupData.GetImageViewArray(imageInputIndex);
argBuffer.UpdateImageViews(shaderInputImage, imageInputIndex, imageViews);
++shaderInputIndex;
}
shaderInputIndex = 0;
for (const RHI::ShaderInputSamplerDescriptor& shaderInputSampler : layout->GetShaderInputListForSamplers())
{
const RHI::ShaderInputSamplerIndex samplerInputIndex(shaderInputIndex);
AZStd::array_view<RHI::SamplerState> samplerStates = groupData.GetSamplerArray(samplerInputIndex);
argBuffer.UpdateSamplers(shaderInputSampler, samplerInputIndex, samplerStates);
++shaderInputIndex;
}
shaderInputIndex = 0;
for (const RHI::ShaderInputBufferDescriptor& shaderInputBuffer : layout->GetShaderInputListForBuffers())
{
const RHI::ShaderInputBufferIndex bufferInputIndex(shaderInputIndex);
AZStd::array_view<RHI::ConstPtr<RHI::BufferView>> bufferViews = groupData.GetBufferViewArray(bufferInputIndex);
argBuffer.UpdateBufferViews(shaderInputBuffer, bufferInputIndex, bufferViews);
++shaderInputIndex;
}
return RHI::ResultCode::Success;
}
void ShaderResourceGroupPool::OnFrameEnd()
{
Base::OnFrameEnd();
}
}
}