Skip to content

[10.x] Metal support updates [Hold] #1795

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 14 commits into
base: HDRP/staging
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,6 @@
"com.unity.ide.vscode": "1.0.7",
"com.unity.multiplayer-hlapi": "1.0.2",
"com.unity.package-manager-ui": "2.2.0",
"com.unity.purchasing": "2.0.6",
"com.unity.render-pipelines.core": "file:../../../com.unity.render-pipelines.core",
"com.unity.render-pipelines.high-definition": "file:../../../com.unity.render-pipelines.high-definition",
"com.unity.shadergraph": "file:../../../com.unity.shadergraph",
Expand Down
1 change: 0 additions & 1 deletion TestProjects/HDRP_DXR_Tests/Packages/manifest.json
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,6 @@
"com.unity.collab-proxy": "1.3.7",
"com.unity.ide.visualstudio": "2.0.0",
"com.unity.ide.vscode": "1.1.4",
"com.unity.purchasing": "2.0.6",
"com.unity.render-pipelines.core": "file:../../../com.unity.render-pipelines.core",
"com.unity.render-pipelines.high-definition": "file:../../../com.unity.render-pipelines.high-definition",
"com.unity.render-pipelines.high-definition-config": "file:../../../com.unity.render-pipelines.high-definition-config",
Expand Down
7 changes: 0 additions & 7 deletions TestProjects/HDRP_HybridTests/Packages/packages-lock.json
Original file line number Diff line number Diff line change
Expand Up @@ -199,13 +199,6 @@
},
"url": "https://artifactory.prd.cds.internal.unity3d.com/artifactory/api/npm/upm-candidates"
},
"com.unity.purchasing": {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

"version": "2.0.6",
"depth": 0,
"source": "registry",
"dependencies": {},
"url": "https://artifactory.prd.cds.internal.unity3d.com/artifactory/api/npm/upm-candidates"
},
"com.unity.render-pipelines.core": {
"version": "file:../../../com.unity.render-pipelines.core",
"depth": 0,
Expand Down
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
7 changes: 0 additions & 7 deletions TestProjects/UniversalHybridTest/Packages/packages-lock.json
Original file line number Diff line number Diff line change
Expand Up @@ -191,13 +191,6 @@
},
"url": "https://artifactory.prd.cds.internal.unity3d.com/artifactory/api/npm/upm-candidates"
},
"com.unity.purchasing": {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

"version": "2.0.6",
"depth": 0,
"source": "registry",
"dependencies": {},
"url": "https://artifactory.prd.cds.internal.unity3d.com/artifactory/api/npm/upm-candidates"
},
"com.unity.render-pipelines.core": {
"version": "file:../../../com.unity.render-pipelines.core",
"depth": 0,
Expand Down
52 changes: 52 additions & 0 deletions com.unity.render-pipelines.core/Runtime/Textures/MSAASamples.cs
Original file line number Diff line number Diff line change
@@ -1,3 +1,7 @@
using System;
using UnityEngine;
using UnityEngine.Experimental.Rendering;

namespace UnityEngine.Rendering
{
/// <summary>
Expand All @@ -14,4 +18,52 @@ public enum MSAASamples
/// <summary>MSAA 8X.</summary>
MSAA8x = 8
}

public static class MSAASamplesExtensions
Copy link
Contributor

@JulienIgnace-Unity JulienIgnace-Unity Sep 21, 2020

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

There is currently no point in making this public so I think we should make it internal.

{
public static FormatUsage AsFormatUsage(this MSAASamples samples)
{
switch (samples)
{
case MSAASamples.MSAA2x:
return FormatUsage.MSAA2x;
case MSAASamples.MSAA4x:
return FormatUsage.MSAA4x;
case MSAASamples.MSAA8x:
return FormatUsage.MSAA8x;
default:
return FormatUsage.Render;
}
}

public static MSAASamples Validate(this MSAASamples samples)
{
if (samples == MSAASamples.None)
return samples;

GraphicsFormat ldrFormat = SystemInfo.GetGraphicsFormat(DefaultFormat.LDR);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why do you use SystemInfo.GetGraphicsFormat(DefaultFormat.LDR); ? to check this.
We need to check every format that will use MSAA.
i.e ColorBufferFormat (which can be selected to be RGBA8 and RGBA16F) for example and other RT like R32 we use for depth in prepass when MSAA is enabled and other stuff. We don't have a single format here.

Is the intent of this function to only check if RGBA8 MSAA sample count is supported or I miss something?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The idea is to use any texture format to figure out what is the generic supported range of MSAA samples on your GfxDevice, it's an improvement over to current assumption.

I don't think our C# APIs have any better way to query a supported MSAA range in other way (if your GfxDevice doesn't support 8x but 2/4 only, or if some really old GPUs wouldn't support 2x). Shaders could pick up some 8x variant for MSTextures use, so this isn't something that we can silently fallback underneath SRP within GfxDevice implementation.

MSAASamples[] probe = {MSAASamples.MSAA2x, MSAASamples.MSAA4x, MSAASamples.MSAA8x};
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is dangerous, if we add MSAA16x in the future this will not be catch, we should generate the array from the enum .
i.e var valuesAsArray = Enum.GetValues(typeof(Enumnum));

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

How are you suggesting to automatically handle MSAASamples.MSAAx mapping into FormatUsage.MSAAx that would still be a problem?


int minSampleCount = 0;
int maxSampleCount = 0;

// Some GPUs might not support MSAA2x, so probe the supported range for clamping
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Maybe comment that it is for Metal API . Other platform don't have this problem

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I believe some APIs allow for the implementation to give you a different sample count than you asked for, but I'm not sure we can always probe for that. Maybe Antti can clarify what this is defending against.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Apple GPUs don't support MSAA 8x, but if we're checking the highest "generic format" MSAA range supported, you might as well check what is the lowest, because historically there has been GPUs outside of Metal domain that haven't supported 2x, but 4x only.

foreach (MSAASamples entry in probe)
{
bool supported = SystemInfo.IsFormatSupported(ldrFormat, entry.AsFormatUsage());
if (!supported)
continue;
if (minSampleCount == 0)
minSampleCount = maxSampleCount = (int)entry;
maxSampleCount = (int)entry;
}

MSAASamples origSampleCount = samples;
samples = (MSAASamples) Math.Min(Math.Max((int) samples, minSampleCount), maxSampleCount);

if (origSampleCount != samples)
Debug.LogWarning($"MSAASamples changed from {origSampleCount} into {samples} (Supported MSAA sampleCount range {minSampleCount}-{maxSampleCount})");
return samples;
}
}
}
37 changes: 37 additions & 0 deletions com.unity.render-pipelines.core/Runtime/Textures/TextureXR.cs
Original file line number Diff line number Diff line change
Expand Up @@ -42,12 +42,37 @@ public static bool useTexArray
case GraphicsDeviceType.Vulkan:
return true;

// VFX basically depends on texture arrays, so TextureXR should be enabled even on platforms without SPI support
// SPI technically available on Metal, but due to fragmented OS/GPU matrix, let's not enable it yet
case GraphicsDeviceType.Metal:
return true;

default:
return false;
}
}
}

// Must be in sync with shader define in TextureXR.hlsl
/// <summary>
/// Returns true if the XR system uses texture arrays for MSAA.
/// </summary>
public static bool useTexArrayMSAA
{
get
{
switch (SystemInfo.graphicsDeviceType)
{
// Metal supports texture arrays with MSAA, but due to fragmented OS/GPU matrix, let's not enable it yet
case GraphicsDeviceType.Metal:
return false;

default:
return useTexArray;
}
}
}

/// <summary>
/// Dimension of XR textures.
/// </summary>
Expand All @@ -60,6 +85,18 @@ public static TextureDimension dimension
}
}

/// <summary>
/// Dimension of XR MSAA textures.
/// </summary>
public static TextureDimension dimensionMSAA
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please do no add this extra API just for Metal.
Let's fix the VFX Graph instead to deal correctly with non-array.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ok.. so we've had these known issues in Spaceship demo's main menu (an on purpose screen glitch is gray instead of coloured) and VFX sparkles not bouncing off from the surfaces as expected, and we've had people working on this project and talking about this limitation/difference against Metal backend a year now? :)

All discussions so far that I've seen suggest that there's something in Metal that should be fixed. But we really can't move on to enabling SPI/XR stuff anytime soon, and on some platforms you shouldn't expect XR/SPI at all.

It makes sense for VFX to share TextureXR, but it's showing this problem where it's clearly depending on an API that locks you into XR/SPI assumptions, VFXGraph should work on targets without SPI too, where you still have texture arrays available.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes problem with this is that the "correct" fix is tricky:

  • We can add a type for CameraBuffers in VFX Graph that will abstract the actual TextureXR. Problem with that is that we lose some interoperability with Shader Graph (as they sont support TextureXR)... So we have a problem UX wise here.

Or we can also solve it by not having TextureXR leak outside of shader code which means SPR API to access camera buffer always return Texture2D (Was the case before but it was changed for RTX I dont exactly remember why). We could also fix the interop issues by allowing a Texture2D view on a texture2DArray first slice...

But I agree with Fabien that fixing it just by changing the type in metal is not an actual fix. Issues still remain for other platforms that dont support XR like XBox for instance.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

And also a problem of when stuff can get properly fixed vs having something working in the meanwhile :) My changes are not super intrusive though within TextureXR, and it will allow fixing the same issue on other platforms without XR/SPI as needed, but of course I tried to restrict actual changes to Metal runtime only when possible

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The MSAA texture array support situation is more unfortunate though. We always have features that "not everyone" depends on automatically, but even on current desktop mac gpu feature table, the availability depends too much to make it a hard requirement. For iOS it's simply not available at all

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sure, but it will add a new public API that we'll have to maintain for many years ... let's please avoid that and fix the root issue.
@julienf-unity : is the Xbox issue tracked anywhere? I'll be happy to help out with fixing VFX/Shader Graph to properly support texarray or not.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@fabien-unity how do we fix the root issue of having a Graphics Device without MSAA texture support, other than not using it when it's not available? :) It's a less common problem than limited XR/SPI availability, but equally could happen elsewhere too than just Metal. The main interest for HDRP users is deferred rendering in any case

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@fabien-unity Xbox issue is tracked via a single ticket for some failing graphics tests. specifically the depth collision one. https://fogbugz.unity3d.com/f/cases/1256635/

We can have a meeting to talk about how to fix the TextureXR issue. @JulienIgnace-Unity you might want to be here.

{
get
{
// TEXTURE2D_X_MSAA/LOAD_TEXTURE2D_X_MSAA macros will now expand to TEXTURE2D or TEXTURE2D_ARRAY
return useTexArrayMSAA ? TextureDimension.Tex2DArray : TextureDimension.Tex2D;
}
}

// Need to keep both the Texture and the RTHandle in order to be able to track lifetime properly.
static Texture m_BlackUIntTexture2DArray;
static Texture m_BlackUIntTexture;
Expand Down
8 changes: 4 additions & 4 deletions com.unity.render-pipelines.core/ShaderLibrary/API/GLES3.hlsl
Original file line number Diff line number Diff line change
Expand Up @@ -52,15 +52,15 @@
#define TEXTURE3D(textureName) Texture3D textureName

#define TEXTURE2D_FLOAT(textureName) Texture2D_float textureName
#define TEXTURE2D_ARRAY_FLOAT(textureName) Texture2DArray textureName // no support to _float on Array, it's being added
#define TEXTURE2D_ARRAY_FLOAT(textureName) Texture2DArray_float textureName
#define TEXTURECUBE_FLOAT(textureName) TextureCube_float textureName
#define TEXTURECUBE_ARRAY_FLOAT(textureName) TextureCubeArray textureName // no support to _float on Array, it's being added
#define TEXTURECUBE_ARRAY_FLOAT(textureName) TextureCubeArray_float textureName
#define TEXTURE3D_FLOAT(textureName) Texture3D_float textureName

#define TEXTURE2D_HALF(textureName) Texture2D_half textureName
#define TEXTURE2D_ARRAY_HALF(textureName) Texture2DArray textureName // no support to _float on Array, it's being added
#define TEXTURE2D_ARRAY_HALF(textureName) Texture2DArray_half textureName
#define TEXTURECUBE_HALF(textureName) TextureCube_half textureName
#define TEXTURECUBE_ARRAY_HALF(textureName) TextureCubeArray textureName // no support to _float on Array, it's being added
#define TEXTURECUBE_ARRAY_HALF(textureName) TextureCubeArray_half textureName
#define TEXTURE3D_HALF(textureName) Texture3D_half textureName

#define TEXTURE2D_SHADOW(textureName) TEXTURE2D(textureName)
Expand Down
8 changes: 4 additions & 4 deletions com.unity.render-pipelines.core/ShaderLibrary/API/Metal.hlsl
Original file line number Diff line number Diff line change
Expand Up @@ -44,15 +44,15 @@
#define TEXTURE3D(textureName) Texture3D textureName

#define TEXTURE2D_FLOAT(textureName) Texture2D_float textureName
#define TEXTURE2D_ARRAY_FLOAT(textureName) Texture2DArray textureName // no support to _float on Array, it's being added
#define TEXTURE2D_ARRAY_FLOAT(textureName) Texture2DArray_float textureName
#define TEXTURECUBE_FLOAT(textureName) TextureCube_float textureName
#define TEXTURECUBE_ARRAY_FLOAT(textureName) TextureCubeArray textureName // no support to _float on Array, it's being added
#define TEXTURECUBE_ARRAY_FLOAT(textureName) TextureCubeArray_float textureName
#define TEXTURE3D_FLOAT(textureName) Texture3D_float textureName

#define TEXTURE2D_HALF(textureName) Texture2D_half textureName
#define TEXTURE2D_ARRAY_HALF(textureName) Texture2DArray textureName // no support to _float on Array, it's being added
#define TEXTURE2D_ARRAY_HALF(textureName) Texture2DArray_half textureName
#define TEXTURECUBE_HALF(textureName) TextureCube_half textureName
#define TEXTURECUBE_ARRAY_HALF(textureName) TextureCubeArray textureName // no support to _float on Array, it's being added
#define TEXTURECUBE_ARRAY_HALF(textureName) TextureCubeArray_half textureName
#define TEXTURE3D_HALF(textureName) Texture3D_half textureName

#define TEXTURE2D_SHADOW(textureName) TEXTURE2D(textureName)
Expand Down
8 changes: 4 additions & 4 deletions com.unity.render-pipelines.core/ShaderLibrary/API/Switch.hlsl
Original file line number Diff line number Diff line change
Expand Up @@ -44,15 +44,15 @@
#define TEXTURE3D(textureName) Texture3D textureName

#define TEXTURE2D_FLOAT(textureName) Texture2D_float textureName
#define TEXTURE2D_ARRAY_FLOAT(textureName) Texture2DArray textureName // no support to _float on Array, it's being added
#define TEXTURE2D_ARRAY_FLOAT(textureName) Texture2DArray_float textureName
#define TEXTURECUBE_FLOAT(textureName) TextureCube_float textureName
#define TEXTURECUBE_ARRAY_FLOAT(textureName) TextureCubeArray textureName // no support to _float on Array, it's being added
#define TEXTURECUBE_ARRAY_FLOAT(textureName) TextureCubeArray_float textureName
#define TEXTURE3D_FLOAT(textureName) Texture3D_float textureName

#define TEXTURE2D_HALF(textureName) Texture2D_half textureName
#define TEXTURE2D_ARRAY_HALF(textureName) Texture2DArray textureName // no support to _float on Array, it's being added
#define TEXTURE2D_ARRAY_HALF(textureName) Texture2DArray_half textureName
#define TEXTURECUBE_HALF(textureName) TextureCube_half textureName
#define TEXTURECUBE_ARRAY_HALF(textureName) TextureCubeArray textureName // no support to _float on Array, it's being added
#define TEXTURECUBE_ARRAY_HALF(textureName) TextureCubeArray_half textureName
#define TEXTURE3D_HALF(textureName) Texture3D_half textureName

#define TEXTURE2D_SHADOW(textureName) TEXTURE2D(textureName)
Expand Down
Loading