mirror of
				https://github.com/ryujinx-mirror/ryujinx.git
				synced 2025-11-04 08:18:58 -06:00 
			
		
		
		
	Add support for bindless textures from storage buffer on Vulkan (#6721)
* Halve primitive ID when converting quads to triangles * Shader cache version bump * Add support for bindless textures from storage buffer on Vulkan
This commit is contained in:
		@@ -36,6 +36,7 @@ namespace Ryujinx.Graphics.GAL
 | 
			
		||||
        public readonly bool SupportsMismatchingViewFormat;
 | 
			
		||||
        public readonly bool SupportsCubemapView;
 | 
			
		||||
        public readonly bool SupportsNonConstantTextureOffset;
 | 
			
		||||
        public readonly bool SupportsQuads;
 | 
			
		||||
        public readonly bool SupportsSeparateSampler;
 | 
			
		||||
        public readonly bool SupportsShaderBallot;
 | 
			
		||||
        public readonly bool SupportsShaderBarrierDivergence;
 | 
			
		||||
@@ -93,6 +94,7 @@ namespace Ryujinx.Graphics.GAL
 | 
			
		||||
            bool supportsMismatchingViewFormat,
 | 
			
		||||
            bool supportsCubemapView,
 | 
			
		||||
            bool supportsNonConstantTextureOffset,
 | 
			
		||||
            bool supportsQuads,
 | 
			
		||||
            bool supportsSeparateSampler,
 | 
			
		||||
            bool supportsShaderBallot,
 | 
			
		||||
            bool supportsShaderBarrierDivergence,
 | 
			
		||||
@@ -146,6 +148,7 @@ namespace Ryujinx.Graphics.GAL
 | 
			
		||||
            SupportsMismatchingViewFormat = supportsMismatchingViewFormat;
 | 
			
		||||
            SupportsCubemapView = supportsCubemapView;
 | 
			
		||||
            SupportsNonConstantTextureOffset = supportsNonConstantTextureOffset;
 | 
			
		||||
            SupportsQuads = supportsQuads;
 | 
			
		||||
            SupportsSeparateSampler = supportsSeparateSampler;
 | 
			
		||||
            SupportsShaderBallot = supportsShaderBallot;
 | 
			
		||||
            SupportsShaderBarrierDivergence = supportsShaderBarrierDivergence;
 | 
			
		||||
 
 | 
			
		||||
@@ -18,6 +18,8 @@ namespace Ryujinx.Graphics.Gpu.Shader.DiskCache
 | 
			
		||||
        private readonly ShaderSpecializationState _newSpecState;
 | 
			
		||||
        private readonly int _stageIndex;
 | 
			
		||||
        private readonly bool _isVulkan;
 | 
			
		||||
        private readonly bool _hasGeometryShader;
 | 
			
		||||
        private readonly bool _supportsQuads;
 | 
			
		||||
 | 
			
		||||
        /// <summary>
 | 
			
		||||
        /// Creates a new instance of the cached GPU state accessor for shader translation.
 | 
			
		||||
@@ -29,6 +31,7 @@ namespace Ryujinx.Graphics.Gpu.Shader.DiskCache
 | 
			
		||||
        /// <param name="newSpecState">Shader specialization state of the recompiled shader</param>
 | 
			
		||||
        /// <param name="counts">Resource counts shared across all shader stages</param>
 | 
			
		||||
        /// <param name="stageIndex">Shader stage index</param>
 | 
			
		||||
        /// <param name="hasGeometryShader">Indicates if a geometry shader is present</param>
 | 
			
		||||
        public DiskCacheGpuAccessor(
 | 
			
		||||
            GpuContext context,
 | 
			
		||||
            ReadOnlyMemory<byte> data,
 | 
			
		||||
@@ -36,7 +39,8 @@ namespace Ryujinx.Graphics.Gpu.Shader.DiskCache
 | 
			
		||||
            ShaderSpecializationState oldSpecState,
 | 
			
		||||
            ShaderSpecializationState newSpecState,
 | 
			
		||||
            ResourceCounts counts,
 | 
			
		||||
            int stageIndex) : base(context, counts, stageIndex)
 | 
			
		||||
            int stageIndex,
 | 
			
		||||
            bool hasGeometryShader) : base(context, counts, stageIndex)
 | 
			
		||||
        {
 | 
			
		||||
            _data = data;
 | 
			
		||||
            _cb1Data = cb1Data;
 | 
			
		||||
@@ -44,6 +48,8 @@ namespace Ryujinx.Graphics.Gpu.Shader.DiskCache
 | 
			
		||||
            _newSpecState = newSpecState;
 | 
			
		||||
            _stageIndex = stageIndex;
 | 
			
		||||
            _isVulkan = context.Capabilities.Api == TargetApi.Vulkan;
 | 
			
		||||
            _hasGeometryShader = hasGeometryShader;
 | 
			
		||||
            _supportsQuads = context.Capabilities.SupportsQuads;
 | 
			
		||||
 | 
			
		||||
            if (stageIndex == (int)ShaderStage.Geometry - 1)
 | 
			
		||||
            {
 | 
			
		||||
@@ -100,7 +106,11 @@ namespace Ryujinx.Graphics.Gpu.Shader.DiskCache
 | 
			
		||||
        /// <inheritdoc/>
 | 
			
		||||
        public GpuGraphicsState QueryGraphicsState()
 | 
			
		||||
        {
 | 
			
		||||
            return _oldSpecState.GraphicsState.CreateShaderGraphicsState(!_isVulkan, _isVulkan || _oldSpecState.GraphicsState.YNegateEnabled);
 | 
			
		||||
            return _oldSpecState.GraphicsState.CreateShaderGraphicsState(
 | 
			
		||||
                !_isVulkan,
 | 
			
		||||
                _supportsQuads,
 | 
			
		||||
                _hasGeometryShader,
 | 
			
		||||
                _isVulkan || _oldSpecState.GraphicsState.YNegateEnabled);
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        /// <inheritdoc/>
 | 
			
		||||
 
 | 
			
		||||
@@ -22,7 +22,7 @@ namespace Ryujinx.Graphics.Gpu.Shader.DiskCache
 | 
			
		||||
        private const ushort FileFormatVersionMajor = 1;
 | 
			
		||||
        private const ushort FileFormatVersionMinor = 2;
 | 
			
		||||
        private const uint FileFormatVersionPacked = ((uint)FileFormatVersionMajor << 16) | FileFormatVersionMinor;
 | 
			
		||||
        private const uint CodeGenVersion = 6577;
 | 
			
		||||
        private const uint CodeGenVersion = 5936;
 | 
			
		||||
 | 
			
		||||
        private const string SharedTocFileName = "shared.toc";
 | 
			
		||||
        private const string SharedDataFileName = "shared.data";
 | 
			
		||||
 
 | 
			
		||||
@@ -601,6 +601,8 @@ namespace Ryujinx.Graphics.Gpu.Shader.DiskCache
 | 
			
		||||
 | 
			
		||||
            TargetApi api = _context.Capabilities.Api;
 | 
			
		||||
 | 
			
		||||
            bool hasCachedGs = guestShaders[4].HasValue;
 | 
			
		||||
 | 
			
		||||
            for (int stageIndex = Constants.ShaderStages - 1; stageIndex >= 0; stageIndex--)
 | 
			
		||||
            {
 | 
			
		||||
                if (guestShaders[stageIndex + 1].HasValue)
 | 
			
		||||
@@ -610,7 +612,7 @@ namespace Ryujinx.Graphics.Gpu.Shader.DiskCache
 | 
			
		||||
                    byte[] guestCode = shader.Code;
 | 
			
		||||
                    byte[] cb1Data = shader.Cb1Data;
 | 
			
		||||
 | 
			
		||||
                    DiskCacheGpuAccessor gpuAccessor = new(_context, guestCode, cb1Data, specState, newSpecState, counts, stageIndex);
 | 
			
		||||
                    DiskCacheGpuAccessor gpuAccessor = new(_context, guestCode, cb1Data, specState, newSpecState, counts, stageIndex, hasCachedGs);
 | 
			
		||||
                    TranslatorContext currentStage = DecodeGraphicsShader(gpuAccessor, api, DefaultFlags, 0);
 | 
			
		||||
 | 
			
		||||
                    if (nextStage != null)
 | 
			
		||||
@@ -623,7 +625,7 @@ namespace Ryujinx.Graphics.Gpu.Shader.DiskCache
 | 
			
		||||
                        byte[] guestCodeA = guestShaders[0].Value.Code;
 | 
			
		||||
                        byte[] cb1DataA = guestShaders[0].Value.Cb1Data;
 | 
			
		||||
 | 
			
		||||
                        DiskCacheGpuAccessor gpuAccessorA = new(_context, guestCodeA, cb1DataA, specState, newSpecState, counts, 0);
 | 
			
		||||
                        DiskCacheGpuAccessor gpuAccessorA = new(_context, guestCodeA, cb1DataA, specState, newSpecState, counts, 0, hasCachedGs);
 | 
			
		||||
                        translatorContexts[0] = DecodeGraphicsShader(gpuAccessorA, api, DefaultFlags | TranslationFlags.VertexA, 0);
 | 
			
		||||
                    }
 | 
			
		||||
 | 
			
		||||
@@ -711,7 +713,7 @@ namespace Ryujinx.Graphics.Gpu.Shader.DiskCache
 | 
			
		||||
            GuestCodeAndCbData shader = guestShaders[0].Value;
 | 
			
		||||
            ResourceCounts counts = new();
 | 
			
		||||
            ShaderSpecializationState newSpecState = new(ref specState.ComputeState);
 | 
			
		||||
            DiskCacheGpuAccessor gpuAccessor = new(_context, shader.Code, shader.Cb1Data, specState, newSpecState, counts, 0);
 | 
			
		||||
            DiskCacheGpuAccessor gpuAccessor = new(_context, shader.Code, shader.Cb1Data, specState, newSpecState, counts, 0, false);
 | 
			
		||||
            gpuAccessor.InitializeReservedCounts(tfEnabled: false, vertexAsCompute: false);
 | 
			
		||||
 | 
			
		||||
            TranslatorContext translatorContext = DecodeComputeShader(gpuAccessor, _context.Capabilities.Api, 0);
 | 
			
		||||
 
 | 
			
		||||
@@ -17,6 +17,8 @@ namespace Ryujinx.Graphics.Gpu.Shader
 | 
			
		||||
        private readonly int _stageIndex;
 | 
			
		||||
        private readonly bool _compute;
 | 
			
		||||
        private readonly bool _isVulkan;
 | 
			
		||||
        private readonly bool _hasGeometryShader;
 | 
			
		||||
        private readonly bool _supportsQuads;
 | 
			
		||||
 | 
			
		||||
        /// <summary>
 | 
			
		||||
        /// Creates a new instance of the GPU state accessor for graphics shader translation.
 | 
			
		||||
@@ -25,12 +27,20 @@ namespace Ryujinx.Graphics.Gpu.Shader
 | 
			
		||||
        /// <param name="channel">GPU channel</param>
 | 
			
		||||
        /// <param name="state">Current GPU state</param>
 | 
			
		||||
        /// <param name="stageIndex">Graphics shader stage index (0 = Vertex, 4 = Fragment)</param>
 | 
			
		||||
        public GpuAccessor(GpuContext context, GpuChannel channel, GpuAccessorState state, int stageIndex) : base(context, state.ResourceCounts, stageIndex)
 | 
			
		||||
        /// <param name="hasGeometryShader">Indicates if a geometry shader is present</param>
 | 
			
		||||
        public GpuAccessor(
 | 
			
		||||
            GpuContext context,
 | 
			
		||||
            GpuChannel channel,
 | 
			
		||||
            GpuAccessorState state,
 | 
			
		||||
            int stageIndex,
 | 
			
		||||
            bool hasGeometryShader) : base(context, state.ResourceCounts, stageIndex)
 | 
			
		||||
        {
 | 
			
		||||
            _isVulkan = context.Capabilities.Api == TargetApi.Vulkan;
 | 
			
		||||
            _channel = channel;
 | 
			
		||||
            _state = state;
 | 
			
		||||
            _stageIndex = stageIndex;
 | 
			
		||||
            _isVulkan = context.Capabilities.Api == TargetApi.Vulkan;
 | 
			
		||||
            _hasGeometryShader = hasGeometryShader;
 | 
			
		||||
            _supportsQuads = context.Capabilities.SupportsQuads;
 | 
			
		||||
 | 
			
		||||
            if (stageIndex == (int)ShaderStage.Geometry - 1)
 | 
			
		||||
            {
 | 
			
		||||
@@ -105,7 +115,11 @@ namespace Ryujinx.Graphics.Gpu.Shader
 | 
			
		||||
        /// <inheritdoc/>
 | 
			
		||||
        public GpuGraphicsState QueryGraphicsState()
 | 
			
		||||
        {
 | 
			
		||||
            return _state.GraphicsState.CreateShaderGraphicsState(!_isVulkan, _isVulkan || _state.GraphicsState.YNegateEnabled);
 | 
			
		||||
            return _state.GraphicsState.CreateShaderGraphicsState(
 | 
			
		||||
                !_isVulkan,
 | 
			
		||||
                _supportsQuads,
 | 
			
		||||
                _hasGeometryShader,
 | 
			
		||||
                _isVulkan || _state.GraphicsState.YNegateEnabled);
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        /// <inheritdoc/>
 | 
			
		||||
 
 | 
			
		||||
@@ -106,8 +106,11 @@ namespace Ryujinx.Graphics.Gpu.Shader
 | 
			
		||||
        /// Creates a new graphics state from this state that can be used for shader generation.
 | 
			
		||||
        /// </summary>
 | 
			
		||||
        /// <param name="hostSupportsAlphaTest">Indicates if the host API supports alpha test operations</param>
 | 
			
		||||
        /// <param name="hostSupportsQuads">Indicates if the host API supports quad primitives</param>
 | 
			
		||||
        /// <param name="hasGeometryShader">Indicates if a geometry shader is used</param>
 | 
			
		||||
        /// <param name="originUpperLeft">If true, indicates that the fragment origin is the upper left corner of the viewport, otherwise it is the lower left corner</param>
 | 
			
		||||
        /// <returns>GPU graphics state that can be used for shader translation</returns>
 | 
			
		||||
        public readonly GpuGraphicsState CreateShaderGraphicsState(bool hostSupportsAlphaTest, bool originUpperLeft)
 | 
			
		||||
        public readonly GpuGraphicsState CreateShaderGraphicsState(bool hostSupportsAlphaTest, bool hostSupportsQuads, bool hasGeometryShader, bool originUpperLeft)
 | 
			
		||||
        {
 | 
			
		||||
            AlphaTestOp alphaTestOp;
 | 
			
		||||
 | 
			
		||||
@@ -130,6 +133,9 @@ namespace Ryujinx.Graphics.Gpu.Shader
 | 
			
		||||
                };
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            bool isQuad = Topology == PrimitiveTopology.Quads || Topology == PrimitiveTopology.QuadStrip;
 | 
			
		||||
            bool halvePrimitiveId = !hostSupportsQuads && !hasGeometryShader && isQuad;
 | 
			
		||||
 | 
			
		||||
            return new GpuGraphicsState(
 | 
			
		||||
                EarlyZForce,
 | 
			
		||||
                ConvertToInputTopology(Topology, TessellationMode),
 | 
			
		||||
@@ -149,7 +155,8 @@ namespace Ryujinx.Graphics.Gpu.Shader
 | 
			
		||||
                in FragmentOutputTypes,
 | 
			
		||||
                DualSourceBlendEnable,
 | 
			
		||||
                YNegateEnabled,
 | 
			
		||||
                originUpperLeft);
 | 
			
		||||
                originUpperLeft,
 | 
			
		||||
                halvePrimitiveId);
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        /// <summary>
 | 
			
		||||
 
 | 
			
		||||
@@ -339,7 +339,7 @@ namespace Ryujinx.Graphics.Gpu.Shader
 | 
			
		||||
 | 
			
		||||
                if (gpuVa != 0)
 | 
			
		||||
                {
 | 
			
		||||
                    GpuAccessor gpuAccessor = new(_context, channel, gpuAccessorState, stageIndex);
 | 
			
		||||
                    GpuAccessor gpuAccessor = new(_context, channel, gpuAccessorState, stageIndex, addresses.Geometry != 0);
 | 
			
		||||
                    TranslatorContext currentStage = DecodeGraphicsShader(gpuAccessor, api, DefaultFlags, gpuVa);
 | 
			
		||||
 | 
			
		||||
                    if (nextStage != null)
 | 
			
		||||
 
 | 
			
		||||
@@ -161,6 +161,7 @@ namespace Ryujinx.Graphics.OpenGL
 | 
			
		||||
                supportsBgraFormat: false,
 | 
			
		||||
                supportsR4G4Format: false,
 | 
			
		||||
                supportsR4G4B4A4Format: true,
 | 
			
		||||
                supportsScaledVertexFormats: true,
 | 
			
		||||
                supportsSnormBufferTextureFormat: false,
 | 
			
		||||
                supports5BitComponentFormat: true,
 | 
			
		||||
                supportsSparseBuffer: false,
 | 
			
		||||
@@ -175,7 +176,7 @@ namespace Ryujinx.Graphics.OpenGL
 | 
			
		||||
                supportsMismatchingViewFormat: HwCapabilities.SupportsMismatchingViewFormat,
 | 
			
		||||
                supportsCubemapView: true,
 | 
			
		||||
                supportsNonConstantTextureOffset: HwCapabilities.SupportsNonConstantTextureOffset,
 | 
			
		||||
                supportsScaledVertexFormats: true,
 | 
			
		||||
                supportsQuads: HwCapabilities.SupportsQuads,
 | 
			
		||||
                supportsSeparateSampler: false,
 | 
			
		||||
                supportsShaderBallot: HwCapabilities.SupportsShaderBallot,
 | 
			
		||||
                supportsShaderBarrierDivergence: !(intelWindows || intelUnix),
 | 
			
		||||
 
 | 
			
		||||
@@ -102,6 +102,11 @@ namespace Ryujinx.Graphics.Shader
 | 
			
		||||
        /// </summary>
 | 
			
		||||
        public readonly bool OriginUpperLeft;
 | 
			
		||||
 | 
			
		||||
        /// <summary>
 | 
			
		||||
        /// Indicates that the primitive ID values on the shader should be halved due to quad to triangles conversion.
 | 
			
		||||
        /// </summary>
 | 
			
		||||
        public readonly bool HalvePrimitiveId;
 | 
			
		||||
 | 
			
		||||
        /// <summary>
 | 
			
		||||
        /// Creates a new GPU graphics state.
 | 
			
		||||
        /// </summary>
 | 
			
		||||
@@ -124,6 +129,7 @@ namespace Ryujinx.Graphics.Shader
 | 
			
		||||
        /// <param name="dualSourceBlendEnable">Indicates whether dual source blend is enabled</param>
 | 
			
		||||
        /// <param name="yNegateEnabled">Indicates if negation of the viewport Y axis is enabled</param>
 | 
			
		||||
        /// <param name="originUpperLeft">If true, indicates that the fragment origin is the upper left corner of the viewport, otherwise it is the lower left corner</param>
 | 
			
		||||
        /// <param name="halvePrimitiveId">Indicates that the primitive ID values on the shader should be halved due to quad to triangles conversion</param>
 | 
			
		||||
        public GpuGraphicsState(
 | 
			
		||||
            bool earlyZForce,
 | 
			
		||||
            InputTopology topology,
 | 
			
		||||
@@ -143,7 +149,8 @@ namespace Ryujinx.Graphics.Shader
 | 
			
		||||
            in Array8<AttributeType> fragmentOutputTypes,
 | 
			
		||||
            bool dualSourceBlendEnable,
 | 
			
		||||
            bool yNegateEnabled,
 | 
			
		||||
            bool originUpperLeft)
 | 
			
		||||
            bool originUpperLeft,
 | 
			
		||||
            bool halvePrimitiveId)
 | 
			
		||||
        {
 | 
			
		||||
            EarlyZForce = earlyZForce;
 | 
			
		||||
            Topology = topology;
 | 
			
		||||
@@ -164,6 +171,7 @@ namespace Ryujinx.Graphics.Shader
 | 
			
		||||
            DualSourceBlendEnable = dualSourceBlendEnable;
 | 
			
		||||
            YNegateEnabled = yNegateEnabled;
 | 
			
		||||
            OriginUpperLeft = originUpperLeft;
 | 
			
		||||
            HalvePrimitiveId = halvePrimitiveId;
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -135,6 +135,7 @@ namespace Ryujinx.Graphics.Shader
 | 
			
		||||
                default,
 | 
			
		||||
                false,
 | 
			
		||||
                false,
 | 
			
		||||
                false,
 | 
			
		||||
                false);
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
@@ -84,6 +84,10 @@ namespace Ryujinx.Graphics.Shader.Instructions
 | 
			
		||||
                                value = context.IConvertU32ToFP32(value);
 | 
			
		||||
                            }
 | 
			
		||||
                        }
 | 
			
		||||
                        else if (offset == AttributeConsts.PrimitiveId && context.TranslatorContext.Definitions.HalvePrimitiveId)
 | 
			
		||||
                        {
 | 
			
		||||
                            value = context.ShiftRightS32(value, Const(1));
 | 
			
		||||
                        }
 | 
			
		||||
 | 
			
		||||
                        context.Copy(Register(rd), value);
 | 
			
		||||
                    }
 | 
			
		||||
@@ -187,6 +191,12 @@ namespace Ryujinx.Graphics.Shader.Instructions
 | 
			
		||||
                        }
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                else if (op.Imm10 == AttributeConsts.PrimitiveId && context.TranslatorContext.Definitions.HalvePrimitiveId)
 | 
			
		||||
                {
 | 
			
		||||
                    // If quads are used, but the host does not support them, they need to be converted to triangles.
 | 
			
		||||
                    // Since each quad becomes 2 triangles, we need to compensate here and divide primitive ID by 2.
 | 
			
		||||
                    res = context.ShiftRightS32(res, Const(1));
 | 
			
		||||
                }
 | 
			
		||||
                else if (op.Imm10 == AttributeConsts.FrontFacing && context.TranslatorContext.GpuAccessor.QueryHostHasFrontFacingBug())
 | 
			
		||||
                {
 | 
			
		||||
                    // gl_FrontFacing sometimes has incorrect (flipped) values depending how it is accessed on Intel GPUs.
 | 
			
		||||
 
 | 
			
		||||
@@ -66,9 +66,9 @@ namespace Ryujinx.Graphics.Shader.Translation.Optimizations
 | 
			
		||||
 | 
			
		||||
            if (nvHandle.AsgOp is not Operation handleOp ||
 | 
			
		||||
                handleOp.Inst != Instruction.Load ||
 | 
			
		||||
                handleOp.StorageKind != StorageKind.Input)
 | 
			
		||||
                (handleOp.StorageKind != StorageKind.Input && handleOp.StorageKind != StorageKind.StorageBuffer))
 | 
			
		||||
            {
 | 
			
		||||
                // Right now, we only allow bindless access when the handle comes from a shader input.
 | 
			
		||||
                // Right now, we only allow bindless access when the handle comes from a shader input or storage buffer.
 | 
			
		||||
                // This is an artificial limitation to prevent it from being used in cases where it
 | 
			
		||||
                // would have a large performance impact of loading all textures in the pool.
 | 
			
		||||
                // It might be removed in the future, if we can mitigate the performance impact.
 | 
			
		||||
 
 | 
			
		||||
@@ -45,6 +45,8 @@ namespace Ryujinx.Graphics.Shader.Translation
 | 
			
		||||
        public bool YNegateEnabled => _graphicsState.YNegateEnabled;
 | 
			
		||||
        public bool OriginUpperLeft => _graphicsState.OriginUpperLeft;
 | 
			
		||||
 | 
			
		||||
        public bool HalvePrimitiveId => _graphicsState.HalvePrimitiveId;
 | 
			
		||||
 | 
			
		||||
        public ImapPixelType[] ImapTypes { get; }
 | 
			
		||||
        public bool IaIndexing { get; private set; }
 | 
			
		||||
        public bool OaIndexing { get; private set; }
 | 
			
		||||
 
 | 
			
		||||
@@ -691,6 +691,7 @@ namespace Ryujinx.Graphics.Vulkan
 | 
			
		||||
                supportsBgraFormat: true,
 | 
			
		||||
                supportsR4G4Format: false,
 | 
			
		||||
                supportsR4G4B4A4Format: supportsR4G4B4A4Format,
 | 
			
		||||
                supportsScaledVertexFormats: FormatCapabilities.SupportsScaledVertexFormats(),
 | 
			
		||||
                supportsSnormBufferTextureFormat: true,
 | 
			
		||||
                supports5BitComponentFormat: supports5BitComponentFormat,
 | 
			
		||||
                supportsSparseBuffer: features2.Features.SparseBinding && mainQueueProperties.QueueFlags.HasFlag(QueueFlags.SparseBindingBit),
 | 
			
		||||
@@ -705,7 +706,7 @@ namespace Ryujinx.Graphics.Vulkan
 | 
			
		||||
                supportsMismatchingViewFormat: true,
 | 
			
		||||
                supportsCubemapView: !IsAmdGcn,
 | 
			
		||||
                supportsNonConstantTextureOffset: false,
 | 
			
		||||
                supportsScaledVertexFormats: FormatCapabilities.SupportsScaledVertexFormats(),
 | 
			
		||||
                supportsQuads: false,
 | 
			
		||||
                supportsSeparateSampler: true,
 | 
			
		||||
                supportsShaderBallot: false,
 | 
			
		||||
                supportsShaderBarrierDivergence: Vendor != Vendor.Intel,
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user