summaryrefslogtreecommitdiffstats
path: root/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11
diff options
context:
space:
mode:
Diffstat (limited to 'src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11')
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Blit11.cpp2486
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Blit11.h230
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Buffer11.cpp1379
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Buffer11.h174
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Clear11.cpp1152
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Clear11.h105
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Context11.cpp405
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Context11.h155
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/DebugAnnotator11.cpp47
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/DebugAnnotator11.h6
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Fence11.cpp107
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Fence11.h11
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Framebuffer11.cpp461
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Framebuffer11.h78
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Image11.cpp591
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Image11.h67
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/IndexBuffer11.cpp62
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/IndexBuffer11.h23
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/InputLayoutCache.cpp464
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/InputLayoutCache.h142
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/NativeWindow.h97
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/NativeWindow11.h38
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/PixelTransfer11.cpp205
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/PixelTransfer11.h34
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/ProgramPipeline11.cpp24
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/ProgramPipeline11.h27
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Query11.cpp363
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Query11.h47
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/RenderStateCache.cpp521
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/RenderStateCache.h137
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/RenderTarget11.cpp359
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/RenderTarget11.h90
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Renderer11.cpp4100
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Renderer11.h573
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/ResourceManager11.cpp533
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/ResourceManager11.h366
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/ShaderExecutable11.cpp111
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/ShaderExecutable11.h45
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/StateManager11.cpp2797
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/StateManager11.h484
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/StreamProducerNV12.cpp102
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/StreamProducerNV12.h44
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/SwapChain11.cpp756
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/SwapChain11.h123
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/TextureStorage11.cpp3701
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/TextureStorage11.h555
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/TransformFeedback11.cpp124
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/TransformFeedback11.h60
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Trim11.cpp9
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Trim11.h4
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/VertexArray11.cpp413
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/VertexArray11.h82
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/VertexBuffer11.cpp149
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/VertexBuffer11.h25
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/copyvertex.inl45
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/dxgi_format_data.json118
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/dxgi_format_map_autogen.cpp516
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/dxgi_support_data.json623
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/dxgi_support_table.cpp1896
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/dxgi_support_table.h5
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/formatutils11.cpp1142
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/formatutils11.h56
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/gen_load_functions_table.cpp0
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/internal_format_initializer_table.cpp170
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/internal_format_initializer_table.h31
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/load_functions_data.json1116
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/load_functions_table.h31
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/load_functions_table_autogen.cpp2098
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/renderer11_utils.cpp2461
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/renderer11_utils.h375
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/shaders/Clear11.hlsl644
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/shaders/MultiplyAlpha.hlsl131
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/shaders/Passthrough2D11.hlsl11
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/shaders/ResolveDepthStencil.hlsl56
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgba2dms11ps.h155
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/swizzle_format_data.json77
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/swizzle_format_info.h51
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/swizzle_format_info_autogen.cpp203
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/texture_format_data.json1199
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/texture_format_map.json78
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/texture_format_table.cpp35
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/texture_format_table.h89
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/texture_format_table_autogen.cpp3037
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/texture_format_table_utils.h85
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/win32/NativeWindow11Win32.cpp (renamed from src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/win32/NativeWindow.cpp)147
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/win32/NativeWindow11Win32.h53
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/CoreWindowNativeWindow.cpp67
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/CoreWindowNativeWindow.h48
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/InspectableNativeWindow.cpp131
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/InspectableNativeWindow.h38
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/NativeWindow11WinRT.cpp126
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/NativeWindow11WinRT.h51
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/SwapChainPanelNativeWindow.cpp63
-rw-r--r--src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/SwapChainPanelNativeWindow.h10
94 files changed, 24381 insertions, 18130 deletions
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Blit11.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Blit11.cpp
index e951e13408..f032e888f1 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Blit11.cpp
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Blit11.cpp
@@ -10,112 +10,404 @@
#include <float.h>
+#include "common/utilities.h"
#include "libANGLE/formatutils.h"
+#include "libANGLE/renderer/d3d/d3d11/RenderTarget11.h"
#include "libANGLE/renderer/d3d/d3d11/Renderer11.h"
-#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
#include "libANGLE/renderer/d3d/d3d11/formatutils11.h"
+#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
+#include "libANGLE/renderer/d3d/d3d11/texture_format_table.h"
#include "third_party/trace_event/trace_event.h"
+namespace rx
+{
+
+namespace
+{
+
+// Include inline shaders in the anonymous namespace to make sure no symbols are exported
#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthrough2d11vs.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthrougha2d11ps.h"
#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughdepth2d11ps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgba2d11ps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgba2dui11ps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgba2di11ps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgb2d11ps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgb2dui11ps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgb2di11ps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrg2d11ps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrg2dui11ps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrg2di11ps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughr2d11ps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughr2dui11ps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughr2di11ps.h"
#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughlum2d11ps.h"
#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughlumalpha2d11ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughr2d11ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughr2di11ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughr2dui11ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrg2d11ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrg2di11ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrg2dui11ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgb2d11ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgb2di11ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgb2dui11ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgba2d11ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgba2di11ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgba2dui11ps.h"
+
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/multiplyalpha_ftof_pm_luma_ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/multiplyalpha_ftof_pm_lumaalpha_ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/multiplyalpha_ftof_pm_rgb_ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/multiplyalpha_ftof_pm_rgba_ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/multiplyalpha_ftof_um_luma_ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/multiplyalpha_ftof_um_lumaalpha_ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/multiplyalpha_ftof_um_rgb_ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/multiplyalpha_ftof_um_rgba_ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/multiplyalpha_ftou_pm_rgb_ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/multiplyalpha_ftou_pm_rgba_ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/multiplyalpha_ftou_pt_rgb_ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/multiplyalpha_ftou_pt_rgba_ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/multiplyalpha_ftou_um_rgb_ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/multiplyalpha_ftou_um_rgba_ps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthrough3d11vs.h"
#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthrough3d11gs.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgba3d11ps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgba3dui11ps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgba3di11ps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgb3d11ps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgb3dui11ps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgb3di11ps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrg3d11ps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrg3dui11ps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrg3di11ps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughr3d11ps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughr3dui11ps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughr3di11ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthrough3d11vs.h"
#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughlum3d11ps.h"
#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughlumalpha3d11ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughr3d11ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughr3di11ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughr3dui11ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrg3d11ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrg3di11ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrg3dui11ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgb3d11ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgb3di11ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgb3dui11ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgba3d11ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgba3di11ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgba3dui11ps.h"
+
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/resolvedepth11_ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/resolvedepthstencil11_ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/resolvedepthstencil11_vs.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/resolvestencil11_ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/swizzlef2darrayps.h"
#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/swizzlef2dps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/swizzlei2dps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/swizzleui2dps.h"
#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/swizzlef3dps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/swizzlei3dps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/swizzleui3dps.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/swizzlef2darrayps.h"
#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/swizzlei2darrayps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/swizzlei2dps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/swizzlei3dps.h"
#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/swizzleui2darrayps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/swizzleui2dps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/swizzleui3dps.h"
-namespace rx
+void StretchedBlitNearest_RowByRow(const gl::Box &sourceArea,
+ const gl::Box &destArea,
+ const gl::Rectangle &clippedDestArea,
+ const gl::Extents &sourceSize,
+ unsigned int sourceRowPitch,
+ unsigned int destRowPitch,
+ size_t pixelSize,
+ const uint8_t *sourceData,
+ uint8_t *destData)
{
+ int srcHeightSubOne = (sourceArea.height - 1);
+ size_t copySize = pixelSize * destArea.width;
+ size_t srcOffset = sourceArea.x * pixelSize;
+ size_t destOffset = destArea.x * pixelSize;
-namespace
+ for (int y = clippedDestArea.y; y < clippedDestArea.y + clippedDestArea.height; y++)
+ {
+ float yPerc = static_cast<float>(y - destArea.y) / (destArea.height - 1);
+
+ // Interpolate using the original source rectangle to determine which row to sample from
+ // while clamping to the edges
+ unsigned int readRow = static_cast<unsigned int>(
+ gl::clamp(sourceArea.y + floor(yPerc * srcHeightSubOne + 0.5f), 0, srcHeightSubOne));
+ unsigned int writeRow = y;
+
+ const uint8_t *sourceRow = sourceData + readRow * sourceRowPitch + srcOffset;
+ uint8_t *destRow = destData + writeRow * destRowPitch + destOffset;
+ memcpy(destRow, sourceRow, copySize);
+ }
+}
+
+void StretchedBlitNearest_PixelByPixel(const gl::Box &sourceArea,
+ const gl::Box &destArea,
+ const gl::Rectangle &clippedDestArea,
+ const gl::Extents &sourceSize,
+ unsigned int sourceRowPitch,
+ unsigned int destRowPitch,
+ ptrdiff_t readOffset,
+ ptrdiff_t writeOffset,
+ size_t copySize,
+ size_t srcPixelStride,
+ size_t destPixelStride,
+ const uint8_t *sourceData,
+ uint8_t *destData)
{
+ auto xMax = clippedDestArea.x + clippedDestArea.width;
+ auto yMax = clippedDestArea.y + clippedDestArea.height;
-DXGI_FORMAT GetTextureFormat(ID3D11Resource *resource)
+ for (int writeRow = clippedDestArea.y; writeRow < yMax; writeRow++)
+ {
+ // Interpolate using the original source rectangle to determine which row to sample from
+ // while clamping to the edges
+ float yPerc = static_cast<float>(writeRow - destArea.y) / (destArea.height - 1);
+ float yRounded = floor(yPerc * (sourceArea.height - 1) + 0.5f);
+ unsigned int readRow =
+ static_cast<unsigned int>(gl::clamp(sourceArea.y + yRounded, 0, sourceSize.height - 1));
+
+ for (int writeColumn = clippedDestArea.x; writeColumn < xMax; writeColumn++)
+ {
+ // Interpolate the original source rectangle to determine which column to sample
+ // from while clamping to the edges
+ float xPerc = static_cast<float>(writeColumn - destArea.x) / (destArea.width - 1);
+ float xRounded = floor(xPerc * (sourceArea.width - 1) + 0.5f);
+ unsigned int readColumn = static_cast<unsigned int>(
+ gl::clamp(sourceArea.x + xRounded, 0, sourceSize.height - 1));
+
+ const uint8_t *sourcePixel =
+ sourceData + readRow * sourceRowPitch + readColumn * srcPixelStride + readOffset;
+
+ uint8_t *destPixel =
+ destData + writeRow * destRowPitch + writeColumn * destPixelStride + writeOffset;
+
+ memcpy(destPixel, sourcePixel, copySize);
+ }
+ }
+}
+
+void StretchedBlitNearest(const gl::Box &sourceArea,
+ const gl::Box &destArea,
+ const gl::Rectangle &clipRect,
+ const gl::Extents &sourceSize,
+ unsigned int sourceRowPitch,
+ unsigned int destRowPitch,
+ ptrdiff_t readOffset,
+ ptrdiff_t writeOffset,
+ size_t copySize,
+ size_t srcPixelStride,
+ size_t destPixelStride,
+ const uint8_t *sourceData,
+ uint8_t *destData)
{
- ID3D11Texture2D *texture = d3d11::DynamicCastComObject<ID3D11Texture2D>(resource);
- if (!texture)
+ gl::Rectangle clippedDestArea(destArea.x, destArea.y, destArea.width, destArea.height);
+ gl::ClipRectangle(clippedDestArea, clipRect, &clippedDestArea);
+
+ // Determine if entire rows can be copied at once instead of each individual pixel. There
+ // must be no out of bounds lookups, whole rows copies, and no scale.
+ if (sourceArea.width == clippedDestArea.width && sourceArea.x >= 0 &&
+ sourceArea.x + sourceArea.width <= sourceSize.width && copySize == srcPixelStride &&
+ copySize == destPixelStride)
+ {
+ StretchedBlitNearest_RowByRow(sourceArea, destArea, clippedDestArea, sourceSize,
+ sourceRowPitch, destRowPitch, srcPixelStride, sourceData,
+ destData);
+ }
+ else
{
- return DXGI_FORMAT_UNKNOWN;
+ StretchedBlitNearest_PixelByPixel(sourceArea, destArea, clippedDestArea, sourceSize,
+ sourceRowPitch, destRowPitch, readOffset, writeOffset,
+ copySize, srcPixelStride, destPixelStride, sourceData,
+ destData);
}
+}
- D3D11_TEXTURE2D_DESC desc;
- texture->GetDesc(&desc);
+using DepthStencilLoader = void(const float *, uint8_t *);
- SafeRelease(texture);
+void LoadDepth16(const float *source, uint8_t *dest)
+{
+ uint32_t convertedDepth = gl::floatToNormalized<16, uint32_t>(source[0]);
+ memcpy(dest, &convertedDepth, 2u);
+}
- return desc.Format;
+void LoadDepth24(const float *source, uint8_t *dest)
+{
+ uint32_t convertedDepth = gl::floatToNormalized<24, uint32_t>(source[0]);
+ memcpy(dest, &convertedDepth, 3u);
}
-ID3D11Resource *CreateStagingTexture(ID3D11Device *device, ID3D11DeviceContext *context,
- ID3D11Resource *source, unsigned int subresource,
- const gl::Extents &size, unsigned int cpuAccessFlags)
+void LoadStencilHelper(const float *source, uint8_t *dest)
{
- D3D11_TEXTURE2D_DESC stagingDesc;
- stagingDesc.Width = size.width;
- stagingDesc.Height = size.height;
- stagingDesc.MipLevels = 1;
- stagingDesc.ArraySize = 1;
- stagingDesc.Format = GetTextureFormat(source);
- stagingDesc.SampleDesc.Count = 1;
- stagingDesc.SampleDesc.Quality = 0;
- stagingDesc.Usage = D3D11_USAGE_STAGING;
- stagingDesc.CPUAccessFlags = cpuAccessFlags;
- stagingDesc.MiscFlags = 0;
- stagingDesc.BindFlags = 0;
-
- ID3D11Texture2D *stagingTexture = nullptr;
- HRESULT result = device->CreateTexture2D(&stagingDesc, nullptr, &stagingTexture);
- if (FAILED(result))
+ uint32_t convertedStencil = gl::getShiftedData<8, 0>(static_cast<uint32_t>(source[1]));
+ memcpy(dest, &convertedStencil, 1u);
+}
+
+void LoadStencil8(const float *source, uint8_t *dest)
+{
+ // STENCIL_INDEX8 is implemented with D24S8, with the depth bits unused. Writes zero for safety.
+ float zero = 0.0f;
+ LoadDepth24(&zero, &dest[0]);
+ LoadStencilHelper(source, &dest[3]);
+}
+
+void LoadDepth24Stencil8(const float *source, uint8_t *dest)
+{
+ LoadDepth24(source, &dest[0]);
+ LoadStencilHelper(source, &dest[3]);
+}
+
+void LoadDepth32F(const float *source, uint8_t *dest)
+{
+ memcpy(dest, source, sizeof(float));
+}
+
+void LoadDepth32FStencil8(const float *source, uint8_t *dest)
+{
+ LoadDepth32F(source, &dest[0]);
+ LoadStencilHelper(source, &dest[4]);
+}
+
+template <DepthStencilLoader loader>
+void CopyDepthStencil(const gl::Box &sourceArea,
+ const gl::Box &destArea,
+ const gl::Rectangle &clippedDestArea,
+ const gl::Extents &sourceSize,
+ unsigned int sourceRowPitch,
+ unsigned int destRowPitch,
+ ptrdiff_t readOffset,
+ ptrdiff_t writeOffset,
+ size_t copySize,
+ size_t srcPixelStride,
+ size_t destPixelStride,
+ const uint8_t *sourceData,
+ uint8_t *destData)
+{
+ // No stretching or subregions are supported, only full blits.
+ ASSERT(sourceArea == destArea);
+ ASSERT(sourceSize.width == sourceArea.width && sourceSize.height == sourceArea.height &&
+ sourceSize.depth == 1);
+ ASSERT(clippedDestArea.width == sourceSize.width &&
+ clippedDestArea.height == sourceSize.height);
+ ASSERT(readOffset == 0 && writeOffset == 0);
+ ASSERT(destArea.x == 0 && destArea.y == 0);
+
+ for (int row = 0; row < destArea.height; ++row)
+ {
+ for (int column = 0; column < destArea.width; ++column)
+ {
+ ptrdiff_t offset = row * sourceRowPitch + column * srcPixelStride;
+ const float *sourcePixel = reinterpret_cast<const float *>(sourceData + offset);
+
+ uint8_t *destPixel = destData + row * destRowPitch + column * destPixelStride;
+
+ loader(sourcePixel, destPixel);
+ }
+ }
+}
+
+void Depth32FStencil8ToDepth32F(const float *source, float *dest)
+{
+ *dest = *source;
+}
+
+void Depth24Stencil8ToDepth32F(const uint32_t *source, float *dest)
+{
+ uint32_t normDepth = source[0] & 0x00FFFFFF;
+ float floatDepth = gl::normalizedToFloat<24>(normDepth);
+ *dest = floatDepth;
+}
+
+void BlitD24S8ToD32F(const gl::Box &sourceArea,
+ const gl::Box &destArea,
+ const gl::Rectangle &clippedDestArea,
+ const gl::Extents &sourceSize,
+ unsigned int sourceRowPitch,
+ unsigned int destRowPitch,
+ ptrdiff_t readOffset,
+ ptrdiff_t writeOffset,
+ size_t copySize,
+ size_t srcPixelStride,
+ size_t destPixelStride,
+ const uint8_t *sourceData,
+ uint8_t *destData)
+{
+ // No stretching or subregions are supported, only full blits.
+ ASSERT(sourceArea == destArea);
+ ASSERT(sourceSize.width == sourceArea.width && sourceSize.height == sourceArea.height &&
+ sourceSize.depth == 1);
+ ASSERT(clippedDestArea.width == sourceSize.width &&
+ clippedDestArea.height == sourceSize.height);
+ ASSERT(readOffset == 0 && writeOffset == 0);
+ ASSERT(destArea.x == 0 && destArea.y == 0);
+
+ for (int row = 0; row < destArea.height; ++row)
{
- ERR("Failed to create staging texture for depth stencil blit. HRESULT: 0x%X.", result);
- return nullptr;
+ for (int column = 0; column < destArea.width; ++column)
+ {
+ ptrdiff_t offset = row * sourceRowPitch + column * srcPixelStride;
+ const uint32_t *sourcePixel = reinterpret_cast<const uint32_t *>(sourceData + offset);
+
+ float *destPixel =
+ reinterpret_cast<float *>(destData + row * destRowPitch + column * destPixelStride);
+
+ Depth24Stencil8ToDepth32F(sourcePixel, destPixel);
+ }
}
+}
- context->CopySubresourceRegion(stagingTexture, 0, 0, 0, 0, source, subresource, nullptr);
+void BlitD32FS8ToD32F(const gl::Box &sourceArea,
+ const gl::Box &destArea,
+ const gl::Rectangle &clippedDestArea,
+ const gl::Extents &sourceSize,
+ unsigned int sourceRowPitch,
+ unsigned int destRowPitch,
+ ptrdiff_t readOffset,
+ ptrdiff_t writeOffset,
+ size_t copySize,
+ size_t srcPixelStride,
+ size_t destPixelStride,
+ const uint8_t *sourceData,
+ uint8_t *destData)
+{
+ // No stretching or subregions are supported, only full blits.
+ ASSERT(sourceArea == destArea);
+ ASSERT(sourceSize.width == sourceArea.width && sourceSize.height == sourceArea.height &&
+ sourceSize.depth == 1);
+ ASSERT(clippedDestArea.width == sourceSize.width &&
+ clippedDestArea.height == sourceSize.height);
+ ASSERT(readOffset == 0 && writeOffset == 0);
+ ASSERT(destArea.x == 0 && destArea.y == 0);
+
+ for (int row = 0; row < destArea.height; ++row)
+ {
+ for (int column = 0; column < destArea.width; ++column)
+ {
+ ptrdiff_t offset = row * sourceRowPitch + column * srcPixelStride;
+ const float *sourcePixel = reinterpret_cast<const float *>(sourceData + offset);
+ float *destPixel =
+ reinterpret_cast<float *>(destData + row * destRowPitch + column * destPixelStride);
- return stagingTexture;
+ Depth32FStencil8ToDepth32F(sourcePixel, destPixel);
+ }
+ }
+}
+
+Blit11::BlitConvertFunction *GetCopyDepthStencilFunction(GLenum internalFormat)
+{
+ switch (internalFormat)
+ {
+ case GL_DEPTH_COMPONENT16:
+ return &CopyDepthStencil<LoadDepth16>;
+ case GL_DEPTH_COMPONENT24:
+ return &CopyDepthStencil<LoadDepth24>;
+ case GL_DEPTH_COMPONENT32F:
+ return &CopyDepthStencil<LoadDepth32F>;
+ case GL_STENCIL_INDEX8:
+ return &CopyDepthStencil<LoadStencil8>;
+ case GL_DEPTH24_STENCIL8:
+ return &CopyDepthStencil<LoadDepth24Stencil8>;
+ case GL_DEPTH32F_STENCIL8:
+ return &CopyDepthStencil<LoadDepth32FStencil8>;
+ default:
+ UNREACHABLE();
+ return nullptr;
+ }
}
-inline void GenerateVertexCoords(const gl::Box &sourceArea, const gl::Extents &sourceSize,
- const gl::Box &destArea, const gl::Extents &destSize,
- float *x1, float *y1, float *x2, float *y2,
- float *u1, float *v1, float *u2, float *v2)
+inline void GenerateVertexCoords(const gl::Box &sourceArea,
+ const gl::Extents &sourceSize,
+ const gl::Box &destArea,
+ const gl::Extents &destSize,
+ float *x1,
+ float *y1,
+ float *x2,
+ float *y2,
+ float *u1,
+ float *v1,
+ float *u2,
+ float *v2)
{
*x1 = (destArea.x / float(destSize.width)) * 2.0f - 1.0f;
*y1 = ((destSize.height - destArea.y - destArea.height) / float(destSize.height)) * 2.0f - 1.0f;
@@ -128,37 +420,49 @@ inline void GenerateVertexCoords(const gl::Box &sourceArea, const gl::Extents &s
*v2 = (sourceArea.y + sourceArea.height) / float(sourceSize.height);
}
-void Write2DVertices(const gl::Box &sourceArea, const gl::Extents &sourceSize,
- const gl::Box &destArea, const gl::Extents &destSize,
- void *outVertices, unsigned int *outStride, unsigned int *outVertexCount,
+void Write2DVertices(const gl::Box &sourceArea,
+ const gl::Extents &sourceSize,
+ const gl::Box &destArea,
+ const gl::Extents &destSize,
+ void *outVertices,
+ unsigned int *outStride,
+ unsigned int *outVertexCount,
D3D11_PRIMITIVE_TOPOLOGY *outTopology)
{
float x1, y1, x2, y2, u1, v1, u2, v2;
- GenerateVertexCoords(sourceArea, sourceSize, destArea, destSize, &x1, &y1, &x2, &y2, &u1, &v1, &u2, &v2);
+ GenerateVertexCoords(sourceArea, sourceSize, destArea, destSize, &x1, &y1, &x2, &y2, &u1, &v1,
+ &u2, &v2);
- d3d11::PositionTexCoordVertex *vertices = static_cast<d3d11::PositionTexCoordVertex*>(outVertices);
+ d3d11::PositionTexCoordVertex *vertices =
+ static_cast<d3d11::PositionTexCoordVertex *>(outVertices);
d3d11::SetPositionTexCoordVertex(&vertices[0], x1, y1, u1, v2);
d3d11::SetPositionTexCoordVertex(&vertices[1], x1, y2, u1, v1);
d3d11::SetPositionTexCoordVertex(&vertices[2], x2, y1, u2, v2);
d3d11::SetPositionTexCoordVertex(&vertices[3], x2, y2, u2, v1);
- *outStride = sizeof(d3d11::PositionTexCoordVertex);
+ *outStride = sizeof(d3d11::PositionTexCoordVertex);
*outVertexCount = 4;
- *outTopology = D3D_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP;
+ *outTopology = D3D_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP;
}
-void Write3DVertices(const gl::Box &sourceArea, const gl::Extents &sourceSize,
- const gl::Box &destArea, const gl::Extents &destSize,
- void *outVertices, unsigned int *outStride, unsigned int *outVertexCount,
+void Write3DVertices(const gl::Box &sourceArea,
+ const gl::Extents &sourceSize,
+ const gl::Box &destArea,
+ const gl::Extents &destSize,
+ void *outVertices,
+ unsigned int *outStride,
+ unsigned int *outVertexCount,
D3D11_PRIMITIVE_TOPOLOGY *outTopology)
{
ASSERT(sourceSize.depth > 0 && destSize.depth > 0);
float x1, y1, x2, y2, u1, v1, u2, v2;
- GenerateVertexCoords(sourceArea, sourceSize, destArea, destSize, &x1, &y1, &x2, &y2, &u1, &v1, &u2, &v2);
+ GenerateVertexCoords(sourceArea, sourceSize, destArea, destSize, &x1, &y1, &x2, &y2, &u1, &v1,
+ &u2, &v2);
- d3d11::PositionLayerTexCoord3DVertex *vertices = static_cast<d3d11::PositionLayerTexCoord3DVertex*>(outVertices);
+ d3d11::PositionLayerTexCoord3DVertex *vertices =
+ static_cast<d3d11::PositionLayerTexCoord3DVertex *>(outVertices);
for (int i = 0; i < destSize.depth; i++)
{
@@ -173,24 +477,38 @@ void Write3DVertices(const gl::Box &sourceArea, const gl::Extents &sourceSize,
d3d11::SetPositionLayerTexCoord3DVertex(&vertices[i * 6 + 5], x2, y1, i, u2, v2, readDepth);
}
- *outStride = sizeof(d3d11::PositionLayerTexCoord3DVertex);
+ *outStride = sizeof(d3d11::PositionLayerTexCoord3DVertex);
*outVertexCount = destSize.depth * 6;
- *outTopology = D3D_PRIMITIVE_TOPOLOGY_TRIANGLELIST;
+ *outTopology = D3D_PRIMITIVE_TOPOLOGY_TRIANGLELIST;
}
-inline unsigned int GetSwizzleIndex(GLenum swizzle)
+unsigned int GetSwizzleIndex(GLenum swizzle)
{
unsigned int colorIndex = 0;
switch (swizzle)
{
- case GL_RED: colorIndex = 0; break;
- case GL_GREEN: colorIndex = 1; break;
- case GL_BLUE: colorIndex = 2; break;
- case GL_ALPHA: colorIndex = 3; break;
- case GL_ZERO: colorIndex = 4; break;
- case GL_ONE: colorIndex = 5; break;
- default: UNREACHABLE(); break;
+ case GL_RED:
+ colorIndex = 0;
+ break;
+ case GL_GREEN:
+ colorIndex = 1;
+ break;
+ case GL_BLUE:
+ colorIndex = 2;
+ break;
+ case GL_ALPHA:
+ colorIndex = 3;
+ break;
+ case GL_ZERO:
+ colorIndex = 4;
+ break;
+ case GL_ONE:
+ colorIndex = 5;
+ break;
+ default:
+ UNREACHABLE();
+ break;
}
return colorIndex;
@@ -213,30 +531,50 @@ D3D11_BLEND_DESC GetAlphaMaskBlendStateDesc()
return desc;
}
-D3D11_INPUT_ELEMENT_DESC quad2DLayout[] =
-{
- { "POSITION", 0, DXGI_FORMAT_R32G32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0 },
- { "TEXCOORD", 0, DXGI_FORMAT_R32G32_FLOAT, 0, 8, D3D11_INPUT_PER_VERTEX_DATA, 0 },
+D3D11_INPUT_ELEMENT_DESC quad2DLayout[] = {
+ {"POSITION", 0, DXGI_FORMAT_R32G32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
+ {"TEXCOORD", 0, DXGI_FORMAT_R32G32_FLOAT, 0, 8, D3D11_INPUT_PER_VERTEX_DATA, 0},
};
-D3D11_INPUT_ELEMENT_DESC quad3DLayout[] =
-{
- { "POSITION", 0, DXGI_FORMAT_R32G32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0 },
- { "LAYER", 0, DXGI_FORMAT_R32_UINT, 0, 8, D3D11_INPUT_PER_VERTEX_DATA, 0 },
- { "TEXCOORD", 0, DXGI_FORMAT_R32G32B32_FLOAT, 0, 12, D3D11_INPUT_PER_VERTEX_DATA, 0 },
+D3D11_INPUT_ELEMENT_DESC quad3DLayout[] = {
+ {"POSITION", 0, DXGI_FORMAT_R32G32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
+ {"LAYER", 0, DXGI_FORMAT_R32_UINT, 0, 8, D3D11_INPUT_PER_VERTEX_DATA, 0},
+ {"TEXCOORD", 0, DXGI_FORMAT_R32G32B32_FLOAT, 0, 12, D3D11_INPUT_PER_VERTEX_DATA, 0},
};
-} // namespace
+DXGI_FORMAT GetStencilSRVFormat(const d3d11::Format &formatSet)
+{
+ switch (formatSet.texFormat)
+ {
+ case DXGI_FORMAT_R32G8X24_TYPELESS:
+ return DXGI_FORMAT_X32_TYPELESS_G8X24_UINT;
+ case DXGI_FORMAT_R24G8_TYPELESS:
+ return DXGI_FORMAT_X24_TYPELESS_G8_UINT;
+ default:
+ UNREACHABLE();
+ return DXGI_FORMAT_UNKNOWN;
+ }
+}
+
+} // namespace
+
+Blit11::Shader::Shader() = default;
+
+Blit11::Shader::Shader(Shader &&other) = default;
+
+Blit11::Shader::~Shader() = default;
+
+Blit11::Shader &Blit11::Shader::operator=(Blit11::Shader &&other) = default;
Blit11::Blit11(Renderer11 *renderer)
: mRenderer(renderer),
mResourcesInitialized(false),
- mVertexBuffer(nullptr),
- mPointSampler(nullptr),
- mLinearSampler(nullptr),
- mScissorEnabledRasterizerState(nullptr),
- mScissorDisabledRasterizerState(nullptr),
- mDepthStencilState(nullptr),
+ mVertexBuffer(),
+ mPointSampler(),
+ mLinearSampler(),
+ mScissorEnabledRasterizerState(),
+ mScissorDisabledRasterizerState(),
+ mDepthStencilState(),
mQuad2DIL(quad2DLayout,
ArraySize(quad2DLayout),
g_VS_Passthrough2D,
@@ -254,516 +592,552 @@ Blit11::Blit11(Renderer11 *renderer)
mQuad3DVS(g_VS_Passthrough3D, ArraySize(g_VS_Passthrough3D), "Blit11 3D vertex shader"),
mQuad3DGS(g_GS_Passthrough3D, ArraySize(g_GS_Passthrough3D), "Blit11 3D geometry shader"),
mAlphaMaskBlendState(GetAlphaMaskBlendStateDesc(), "Blit11 Alpha Mask Blend"),
- mSwizzleCB(nullptr)
+ mSwizzleCB(),
+ mResolveDepthStencilVS(g_VS_ResolveDepthStencil,
+ ArraySize(g_VS_ResolveDepthStencil),
+ "Blit11::mResolveDepthStencilVS"),
+ mResolveDepthPS(g_PS_ResolveDepth, ArraySize(g_PS_ResolveDepth), "Blit11::mResolveDepthPS"),
+ mResolveDepthStencilPS(g_PS_ResolveDepthStencil,
+ ArraySize(g_PS_ResolveDepthStencil),
+ "Blit11::mResolveDepthStencilPS"),
+ mResolveStencilPS(g_PS_ResolveStencil,
+ ArraySize(g_PS_ResolveStencil),
+ "Blit11::mResolveStencilPS"),
+ mStencilSRV(),
+ mResolvedDepthStencilRTView()
{
}
Blit11::~Blit11()
{
- freeResources();
-
- mQuad2DIL.release();
- mQuad2DVS.release();
- mDepthPS.release();
-
- mQuad3DIL.release();
- mQuad3DVS.release();
- mQuad3DGS.release();
-
- clearShaderMap();
}
gl::Error Blit11::initResources()
{
if (mResourcesInitialized)
{
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
TRACE_EVENT0("gpu.angle", "Blit11::initResources");
- HRESULT result;
- ID3D11Device *device = mRenderer->getDevice();
-
D3D11_BUFFER_DESC vbDesc;
vbDesc.ByteWidth =
static_cast<unsigned int>(std::max(sizeof(d3d11::PositionLayerTexCoord3DVertex),
sizeof(d3d11::PositionTexCoordVertex)) *
- 6 * mRenderer->getRendererCaps().max3DTextureSize);
- vbDesc.Usage = D3D11_USAGE_DYNAMIC;
- vbDesc.BindFlags = D3D11_BIND_VERTEX_BUFFER;
- vbDesc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE;
- vbDesc.MiscFlags = 0;
+ 6 * mRenderer->getNativeCaps().max3DTextureSize);
+ vbDesc.Usage = D3D11_USAGE_DYNAMIC;
+ vbDesc.BindFlags = D3D11_BIND_VERTEX_BUFFER;
+ vbDesc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE;
+ vbDesc.MiscFlags = 0;
vbDesc.StructureByteStride = 0;
- result = device->CreateBuffer(&vbDesc, nullptr, &mVertexBuffer);
- ASSERT(SUCCEEDED(result));
- if (FAILED(result))
- {
- freeResources();
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create blit vertex buffer, HRESULT: 0x%X",
- result);
- }
- d3d11::SetDebugName(mVertexBuffer, "Blit11 vertex buffer");
+ ANGLE_TRY(mRenderer->allocateResource(vbDesc, &mVertexBuffer));
+ mVertexBuffer.setDebugName("Blit11 vertex buffer");
D3D11_SAMPLER_DESC pointSamplerDesc;
- pointSamplerDesc.Filter = D3D11_FILTER_MIN_MAG_POINT_MIP_LINEAR;
- pointSamplerDesc.AddressU = D3D11_TEXTURE_ADDRESS_CLAMP;
- pointSamplerDesc.AddressV = D3D11_TEXTURE_ADDRESS_CLAMP;
- pointSamplerDesc.AddressW = D3D11_TEXTURE_ADDRESS_CLAMP;
- pointSamplerDesc.MipLODBias = 0.0f;
- pointSamplerDesc.MaxAnisotropy = 0;
+ pointSamplerDesc.Filter = D3D11_FILTER_MIN_MAG_POINT_MIP_LINEAR;
+ pointSamplerDesc.AddressU = D3D11_TEXTURE_ADDRESS_CLAMP;
+ pointSamplerDesc.AddressV = D3D11_TEXTURE_ADDRESS_CLAMP;
+ pointSamplerDesc.AddressW = D3D11_TEXTURE_ADDRESS_CLAMP;
+ pointSamplerDesc.MipLODBias = 0.0f;
+ pointSamplerDesc.MaxAnisotropy = 0;
pointSamplerDesc.ComparisonFunc = D3D11_COMPARISON_NEVER;
pointSamplerDesc.BorderColor[0] = 0.0f;
pointSamplerDesc.BorderColor[1] = 0.0f;
pointSamplerDesc.BorderColor[2] = 0.0f;
pointSamplerDesc.BorderColor[3] = 0.0f;
- pointSamplerDesc.MinLOD = 0.0f;
- pointSamplerDesc.MaxLOD = FLT_MAX;
+ pointSamplerDesc.MinLOD = 0.0f;
+ pointSamplerDesc.MaxLOD = FLT_MAX;
- result = device->CreateSamplerState(&pointSamplerDesc, &mPointSampler);
- ASSERT(SUCCEEDED(result));
- if (FAILED(result))
- {
- freeResources();
- return gl::Error(GL_OUT_OF_MEMORY,
- "Failed to create blit point sampler state, HRESULT: 0x%X", result);
- }
- d3d11::SetDebugName(mPointSampler, "Blit11 point sampler");
+ ANGLE_TRY(mRenderer->allocateResource(pointSamplerDesc, &mPointSampler));
+ mPointSampler.setDebugName("Blit11 point sampler");
D3D11_SAMPLER_DESC linearSamplerDesc;
- linearSamplerDesc.Filter = D3D11_FILTER_MIN_MAG_MIP_LINEAR;
- linearSamplerDesc.AddressU = D3D11_TEXTURE_ADDRESS_CLAMP;
- linearSamplerDesc.AddressV = D3D11_TEXTURE_ADDRESS_CLAMP;
- linearSamplerDesc.AddressW = D3D11_TEXTURE_ADDRESS_CLAMP;
- linearSamplerDesc.MipLODBias = 0.0f;
- linearSamplerDesc.MaxAnisotropy = 0;
+ linearSamplerDesc.Filter = D3D11_FILTER_MIN_MAG_MIP_LINEAR;
+ linearSamplerDesc.AddressU = D3D11_TEXTURE_ADDRESS_CLAMP;
+ linearSamplerDesc.AddressV = D3D11_TEXTURE_ADDRESS_CLAMP;
+ linearSamplerDesc.AddressW = D3D11_TEXTURE_ADDRESS_CLAMP;
+ linearSamplerDesc.MipLODBias = 0.0f;
+ linearSamplerDesc.MaxAnisotropy = 0;
linearSamplerDesc.ComparisonFunc = D3D11_COMPARISON_NEVER;
linearSamplerDesc.BorderColor[0] = 0.0f;
linearSamplerDesc.BorderColor[1] = 0.0f;
linearSamplerDesc.BorderColor[2] = 0.0f;
linearSamplerDesc.BorderColor[3] = 0.0f;
- linearSamplerDesc.MinLOD = 0.0f;
- linearSamplerDesc.MaxLOD = FLT_MAX;
+ linearSamplerDesc.MinLOD = 0.0f;
+ linearSamplerDesc.MaxLOD = FLT_MAX;
- result = device->CreateSamplerState(&linearSamplerDesc, &mLinearSampler);
- ASSERT(SUCCEEDED(result));
- if (FAILED(result))
- {
- freeResources();
- return gl::Error(GL_OUT_OF_MEMORY,
- "Failed to create blit linear sampler state, HRESULT: 0x%X", result);
- }
- d3d11::SetDebugName(mLinearSampler, "Blit11 linear sampler");
+ ANGLE_TRY(mRenderer->allocateResource(linearSamplerDesc, &mLinearSampler));
+ mLinearSampler.setDebugName("Blit11 linear sampler");
// Use a rasterizer state that will not cull so that inverted quads will not be culled
D3D11_RASTERIZER_DESC rasterDesc;
- rasterDesc.FillMode = D3D11_FILL_SOLID;
- rasterDesc.CullMode = D3D11_CULL_NONE;
+ rasterDesc.FillMode = D3D11_FILL_SOLID;
+ rasterDesc.CullMode = D3D11_CULL_NONE;
rasterDesc.FrontCounterClockwise = FALSE;
- rasterDesc.DepthBias = 0;
- rasterDesc.SlopeScaledDepthBias = 0.0f;
- rasterDesc.DepthBiasClamp = 0.0f;
- rasterDesc.DepthClipEnable = TRUE;
- rasterDesc.MultisampleEnable = FALSE;
+ rasterDesc.DepthBias = 0;
+ rasterDesc.SlopeScaledDepthBias = 0.0f;
+ rasterDesc.DepthBiasClamp = 0.0f;
+ rasterDesc.DepthClipEnable = TRUE;
+ rasterDesc.MultisampleEnable = FALSE;
rasterDesc.AntialiasedLineEnable = FALSE;
rasterDesc.ScissorEnable = TRUE;
- result = device->CreateRasterizerState(&rasterDesc, &mScissorEnabledRasterizerState);
- ASSERT(SUCCEEDED(result));
- if (FAILED(result))
- {
- freeResources();
- return gl::Error(GL_OUT_OF_MEMORY,
- "Failed to create blit scissoring rasterizer state, HRESULT: 0x%X",
- result);
- }
- d3d11::SetDebugName(mScissorEnabledRasterizerState, "Blit11 scissoring rasterizer state");
+ ANGLE_TRY(mRenderer->allocateResource(rasterDesc, &mScissorEnabledRasterizerState));
+ mScissorEnabledRasterizerState.setDebugName("Blit11 scissoring rasterizer state");
rasterDesc.ScissorEnable = FALSE;
- result = device->CreateRasterizerState(&rasterDesc, &mScissorDisabledRasterizerState);
- ASSERT(SUCCEEDED(result));
- if (FAILED(result))
- {
- freeResources();
- return gl::Error(GL_OUT_OF_MEMORY,
- "Failed to create blit no scissoring rasterizer state, HRESULT: 0x%X",
- result);
- }
- d3d11::SetDebugName(mScissorDisabledRasterizerState, "Blit11 no scissoring rasterizer state");
+ ANGLE_TRY(mRenderer->allocateResource(rasterDesc, &mScissorDisabledRasterizerState));
+ mScissorDisabledRasterizerState.setDebugName("Blit11 no scissoring rasterizer state");
D3D11_DEPTH_STENCIL_DESC depthStencilDesc;
- depthStencilDesc.DepthEnable = true;
- depthStencilDesc.DepthWriteMask = D3D11_DEPTH_WRITE_MASK_ALL;
- depthStencilDesc.DepthFunc = D3D11_COMPARISON_ALWAYS;
- depthStencilDesc.StencilEnable = FALSE;
- depthStencilDesc.StencilReadMask = D3D11_DEFAULT_STENCIL_READ_MASK;
- depthStencilDesc.StencilWriteMask = D3D11_DEFAULT_STENCIL_WRITE_MASK;
- depthStencilDesc.FrontFace.StencilFailOp = D3D11_STENCIL_OP_KEEP;
+ depthStencilDesc.DepthEnable = TRUE;
+ depthStencilDesc.DepthWriteMask = D3D11_DEPTH_WRITE_MASK_ALL;
+ depthStencilDesc.DepthFunc = D3D11_COMPARISON_ALWAYS;
+ depthStencilDesc.StencilEnable = FALSE;
+ depthStencilDesc.StencilReadMask = D3D11_DEFAULT_STENCIL_READ_MASK;
+ depthStencilDesc.StencilWriteMask = D3D11_DEFAULT_STENCIL_WRITE_MASK;
+ depthStencilDesc.FrontFace.StencilFailOp = D3D11_STENCIL_OP_KEEP;
depthStencilDesc.FrontFace.StencilDepthFailOp = D3D11_STENCIL_OP_KEEP;
- depthStencilDesc.FrontFace.StencilPassOp = D3D11_STENCIL_OP_KEEP;
- depthStencilDesc.FrontFace.StencilFunc = D3D11_COMPARISON_ALWAYS;
- depthStencilDesc.BackFace.StencilFailOp = D3D11_STENCIL_OP_KEEP;
- depthStencilDesc.BackFace.StencilDepthFailOp = D3D11_STENCIL_OP_KEEP;
- depthStencilDesc.BackFace.StencilPassOp = D3D11_STENCIL_OP_KEEP;
- depthStencilDesc.BackFace.StencilFunc = D3D11_COMPARISON_ALWAYS;
-
- result = device->CreateDepthStencilState(&depthStencilDesc, &mDepthStencilState);
- ASSERT(SUCCEEDED(result));
- if (FAILED(result))
- {
- freeResources();
- return gl::Error(GL_OUT_OF_MEMORY,
- "Failed to create blit depth stencil state, HRESULT: 0x%X", result);
- }
- d3d11::SetDebugName(mDepthStencilState, "Blit11 depth stencil state");
+ depthStencilDesc.FrontFace.StencilPassOp = D3D11_STENCIL_OP_KEEP;
+ depthStencilDesc.FrontFace.StencilFunc = D3D11_COMPARISON_ALWAYS;
+ depthStencilDesc.BackFace.StencilFailOp = D3D11_STENCIL_OP_KEEP;
+ depthStencilDesc.BackFace.StencilDepthFailOp = D3D11_STENCIL_OP_KEEP;
+ depthStencilDesc.BackFace.StencilPassOp = D3D11_STENCIL_OP_KEEP;
+ depthStencilDesc.BackFace.StencilFunc = D3D11_COMPARISON_ALWAYS;
+
+ ANGLE_TRY(mRenderer->allocateResource(depthStencilDesc, &mDepthStencilState));
+ mDepthStencilState.setDebugName("Blit11 depth stencil state");
D3D11_BUFFER_DESC swizzleBufferDesc;
- swizzleBufferDesc.ByteWidth = sizeof(unsigned int) * 4;
- swizzleBufferDesc.Usage = D3D11_USAGE_DYNAMIC;
- swizzleBufferDesc.BindFlags = D3D11_BIND_CONSTANT_BUFFER;
- swizzleBufferDesc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE;
- swizzleBufferDesc.MiscFlags = 0;
+ swizzleBufferDesc.ByteWidth = sizeof(unsigned int) * 4;
+ swizzleBufferDesc.Usage = D3D11_USAGE_DYNAMIC;
+ swizzleBufferDesc.BindFlags = D3D11_BIND_CONSTANT_BUFFER;
+ swizzleBufferDesc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE;
+ swizzleBufferDesc.MiscFlags = 0;
swizzleBufferDesc.StructureByteStride = 0;
- result = device->CreateBuffer(&swizzleBufferDesc, nullptr, &mSwizzleCB);
- ASSERT(SUCCEEDED(result));
- if (FAILED(result))
- {
- freeResources();
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create blit swizzle buffer, HRESULT: 0x%X",
- result);
- }
- d3d11::SetDebugName(mSwizzleCB, "Blit11 swizzle constant buffer");
+ ANGLE_TRY(mRenderer->allocateResource(swizzleBufferDesc, &mSwizzleCB));
+ mSwizzleCB.setDebugName("Blit11 swizzle constant buffer");
mResourcesInitialized = true;
- return gl::Error(GL_NO_ERROR);
-}
-
-void Blit11::freeResources()
-{
- SafeRelease(mVertexBuffer);
- SafeRelease(mPointSampler);
- SafeRelease(mLinearSampler);
- SafeRelease(mScissorEnabledRasterizerState);
- SafeRelease(mScissorDisabledRasterizerState);
- SafeRelease(mDepthStencilState);
- SafeRelease(mSwizzleCB);
-
- mResourcesInitialized = false;
+ return gl::NoError();
}
// static
-Blit11::BlitShaderType Blit11::GetBlitShaderType(GLenum destinationFormat, bool isSigned, ShaderDimension dimension)
+Blit11::BlitShaderType Blit11::GetBlitShaderType(GLenum destinationFormat,
+ GLenum sourceFormat,
+ bool isSigned,
+ bool unpackPremultiplyAlpha,
+ bool unpackUnmultiplyAlpha,
+ ShaderDimension dimension)
{
if (dimension == SHADER_3D)
{
+ ASSERT(!unpackPremultiplyAlpha && !unpackUnmultiplyAlpha);
+
if (isSigned)
{
switch (destinationFormat)
{
- case GL_RGBA_INTEGER: return BLITSHADER_3D_RGBAI;
- case GL_RGB_INTEGER: return BLITSHADER_3D_RGBI;
- case GL_RG_INTEGER: return BLITSHADER_3D_RGI;
- case GL_RED_INTEGER: return BLITSHADER_3D_RI;
- default:
- UNREACHABLE();
- return BLITSHADER_INVALID;
+ case GL_RGBA_INTEGER:
+ return BLITSHADER_3D_RGBAI;
+ case GL_RGB_INTEGER:
+ return BLITSHADER_3D_RGBI;
+ case GL_RG_INTEGER:
+ return BLITSHADER_3D_RGI;
+ case GL_RED_INTEGER:
+ return BLITSHADER_3D_RI;
+ default:
+ UNREACHABLE();
+ return BLITSHADER_INVALID;
}
}
else
{
switch (destinationFormat)
{
- case GL_RGBA: return BLITSHADER_3D_RGBAF;
- case GL_RGBA_INTEGER: return BLITSHADER_3D_RGBAUI;
- case GL_BGRA_EXT: return BLITSHADER_3D_BGRAF;
- case GL_RGB: return BLITSHADER_3D_RGBF;
- case GL_RGB_INTEGER: return BLITSHADER_3D_RGBUI;
- case GL_RG: return BLITSHADER_3D_RGF;
- case GL_RG_INTEGER: return BLITSHADER_3D_RGUI;
- case GL_RED: return BLITSHADER_3D_RF;
- case GL_RED_INTEGER: return BLITSHADER_3D_RUI;
- case GL_ALPHA: return BLITSHADER_3D_ALPHA;
- case GL_LUMINANCE: return BLITSHADER_3D_LUMA;
- case GL_LUMINANCE_ALPHA: return BLITSHADER_3D_LUMAALPHA;
- default:
- UNREACHABLE();
- return BLITSHADER_INVALID;
+ case GL_RGBA:
+ return BLITSHADER_3D_RGBAF;
+ case GL_RGBA_INTEGER:
+ return BLITSHADER_3D_RGBAUI;
+ case GL_BGRA_EXT:
+ return BLITSHADER_3D_BGRAF;
+ case GL_RGB:
+ return BLITSHADER_3D_RGBF;
+ case GL_RGB_INTEGER:
+ return BLITSHADER_3D_RGBUI;
+ case GL_RG:
+ return BLITSHADER_3D_RGF;
+ case GL_RG_INTEGER:
+ return BLITSHADER_3D_RGUI;
+ case GL_RED:
+ return BLITSHADER_3D_RF;
+ case GL_RED_INTEGER:
+ return BLITSHADER_3D_RUI;
+ case GL_ALPHA:
+ return BLITSHADER_3D_ALPHA;
+ case GL_LUMINANCE:
+ return BLITSHADER_3D_LUMA;
+ case GL_LUMINANCE_ALPHA:
+ return BLITSHADER_3D_LUMAALPHA;
+ default:
+ UNREACHABLE();
+ return BLITSHADER_INVALID;
}
}
}
else if (isSigned)
{
+ ASSERT(!unpackPremultiplyAlpha && !unpackUnmultiplyAlpha);
+
switch (destinationFormat)
{
- case GL_RGBA_INTEGER: return BLITSHADER_2D_RGBAI;
- case GL_RGB_INTEGER: return BLITSHADER_2D_RGBI;
- case GL_RG_INTEGER: return BLITSHADER_2D_RGI;
- case GL_RED_INTEGER: return BLITSHADER_2D_RI;
- default:
- UNREACHABLE();
- return BLITSHADER_INVALID;
+ case GL_RGBA_INTEGER:
+ return BLITSHADER_2D_RGBAI;
+ case GL_RGB_INTEGER:
+ return BLITSHADER_2D_RGBI;
+ case GL_RG_INTEGER:
+ return BLITSHADER_2D_RGI;
+ case GL_RED_INTEGER:
+ return BLITSHADER_2D_RI;
+ default:
+ UNREACHABLE();
+ return BLITSHADER_INVALID;
}
}
else
{
- switch (destinationFormat)
+ bool floatToIntBlit =
+ !gl::IsIntegerFormat(sourceFormat) && gl::IsIntegerFormat(destinationFormat);
+ if (unpackPremultiplyAlpha != unpackUnmultiplyAlpha || floatToIntBlit)
{
- case GL_RGBA: return BLITSHADER_2D_RGBAF;
- case GL_RGBA_INTEGER: return BLITSHADER_2D_RGBAUI;
- case GL_BGRA_EXT: return BLITSHADER_2D_BGRAF;
- case GL_RGB: return BLITSHADER_2D_RGBF;
- case GL_RGB_INTEGER: return BLITSHADER_2D_RGBUI;
- case GL_RG: return BLITSHADER_2D_RGF;
- case GL_RG_INTEGER: return BLITSHADER_2D_RGUI;
- case GL_RED: return BLITSHADER_2D_RF;
- case GL_RED_INTEGER: return BLITSHADER_2D_RUI;
- case GL_ALPHA: return BLITSHADER_2D_ALPHA;
- case GL_LUMINANCE: return BLITSHADER_2D_LUMA;
- case GL_LUMINANCE_ALPHA: return BLITSHADER_2D_LUMAALPHA;
- default:
- UNREACHABLE();
- return BLITSHADER_INVALID;
+ switch (destinationFormat)
+ {
+ case GL_RGBA:
+ case GL_BGRA_EXT:
+ ASSERT(!floatToIntBlit);
+ return unpackPremultiplyAlpha ? BLITSHADER_2D_RGBAF_PREMULTIPLY
+ : BLITSHADER_2D_RGBAF_UNMULTIPLY;
+
+ case GL_RGB:
+ case GL_RG:
+ case GL_RED:
+ ASSERT(!floatToIntBlit);
+ return unpackPremultiplyAlpha ? BLITSHADER_2D_RGBF_PREMULTIPLY
+ : BLITSHADER_2D_RGBF_UNMULTIPLY;
+
+ case GL_RGBA_INTEGER:
+ if (unpackPremultiplyAlpha == unpackUnmultiplyAlpha)
+ {
+ return BLITSHADER_2D_RGBAF_TOUI;
+ }
+ else
+ {
+ return unpackPremultiplyAlpha ? BLITSHADER_2D_RGBAF_TOUI_PREMULTIPLY
+ : BLITSHADER_2D_RGBAF_TOUI_UNMULTIPLY;
+ }
+
+ case GL_RGB_INTEGER:
+ case GL_RG_INTEGER:
+ case GL_RED_INTEGER:
+ if (unpackPremultiplyAlpha == unpackUnmultiplyAlpha)
+ {
+ return BLITSHADER_2D_RGBF_TOUI;
+ }
+ else
+ {
+ return unpackPremultiplyAlpha ? BLITSHADER_2D_RGBF_TOUI_PREMULTIPLY
+ : BLITSHADER_2D_RGBF_TOUI_UNMULTIPLY;
+ }
+ case GL_LUMINANCE:
+ ASSERT(!floatToIntBlit);
+ return unpackPremultiplyAlpha ? BLITSHADER_2D_LUMAF_PREMULTIPLY
+ : BLITSHADER_2D_LUMAF_UNMULTIPLY;
+ case GL_LUMINANCE_ALPHA:
+ ASSERT(!floatToIntBlit);
+ return unpackPremultiplyAlpha ? BLITSHADER_2D_LUMAALPHAF_PREMULTIPLY
+ : BLITSHADER_2D_LUMAALPHAF_UNMULTIPLY;
+ case GL_ALPHA:
+ ASSERT(!floatToIntBlit);
+ return BLITSHADER_2D_ALPHA;
+ default:
+ UNREACHABLE();
+ return BLITSHADER_INVALID;
+ }
+ }
+ else
+ {
+ switch (destinationFormat)
+ {
+ case GL_RGBA:
+ return BLITSHADER_2D_RGBAF;
+ case GL_RGBA_INTEGER:
+ return BLITSHADER_2D_RGBAUI;
+ case GL_BGRA_EXT:
+ return BLITSHADER_2D_BGRAF;
+ case GL_RGB:
+ return BLITSHADER_2D_RGBF;
+ case GL_RGB_INTEGER:
+ return BLITSHADER_2D_RGBUI;
+ case GL_RG:
+ return BLITSHADER_2D_RGF;
+ case GL_RG_INTEGER:
+ return BLITSHADER_2D_RGUI;
+ case GL_RED:
+ return BLITSHADER_2D_RF;
+ case GL_RED_INTEGER:
+ return BLITSHADER_2D_RUI;
+ case GL_ALPHA:
+ return BLITSHADER_2D_ALPHA;
+ case GL_LUMINANCE:
+ return BLITSHADER_2D_LUMA;
+ case GL_LUMINANCE_ALPHA:
+ return BLITSHADER_2D_LUMAALPHA;
+ default:
+ UNREACHABLE();
+ return BLITSHADER_INVALID;
+ }
}
}
}
// static
-Blit11::SwizzleShaderType Blit11::GetSwizzleShaderType(GLenum type, D3D11_SRV_DIMENSION dimensionality)
+Blit11::SwizzleShaderType Blit11::GetSwizzleShaderType(GLenum type,
+ D3D11_SRV_DIMENSION dimensionality)
{
switch (dimensionality)
{
- case D3D11_SRV_DIMENSION_TEXTURE2D:
- switch (type)
- {
- case GL_FLOAT: return SWIZZLESHADER_2D_FLOAT;
- case GL_UNSIGNED_INT: return SWIZZLESHADER_2D_UINT;
- case GL_INT: return SWIZZLESHADER_2D_INT;
- default:
- UNREACHABLE();
- return SWIZZLESHADER_INVALID;
- }
- case D3D11_SRV_DIMENSION_TEXTURECUBE:
- switch (type)
- {
- case GL_FLOAT: return SWIZZLESHADER_CUBE_FLOAT;
- case GL_UNSIGNED_INT: return SWIZZLESHADER_CUBE_UINT;
- case GL_INT: return SWIZZLESHADER_CUBE_INT;
- default:
- UNREACHABLE();
- return SWIZZLESHADER_INVALID;
- }
- case D3D11_SRV_DIMENSION_TEXTURE3D:
- switch (type)
- {
- case GL_FLOAT: return SWIZZLESHADER_3D_FLOAT;
- case GL_UNSIGNED_INT: return SWIZZLESHADER_3D_UINT;
- case GL_INT: return SWIZZLESHADER_3D_INT;
- default:
- UNREACHABLE();
- return SWIZZLESHADER_INVALID;
- }
- case D3D11_SRV_DIMENSION_TEXTURE2DARRAY:
- switch (type)
- {
- case GL_FLOAT: return SWIZZLESHADER_ARRAY_FLOAT;
- case GL_UNSIGNED_INT: return SWIZZLESHADER_ARRAY_UINT;
- case GL_INT: return SWIZZLESHADER_ARRAY_INT;
- default:
+ case D3D11_SRV_DIMENSION_TEXTURE2D:
+ switch (type)
+ {
+ case GL_FLOAT:
+ return SWIZZLESHADER_2D_FLOAT;
+ case GL_UNSIGNED_INT:
+ return SWIZZLESHADER_2D_UINT;
+ case GL_INT:
+ return SWIZZLESHADER_2D_INT;
+ default:
+ UNREACHABLE();
+ return SWIZZLESHADER_INVALID;
+ }
+ case D3D11_SRV_DIMENSION_TEXTURECUBE:
+ switch (type)
+ {
+ case GL_FLOAT:
+ return SWIZZLESHADER_CUBE_FLOAT;
+ case GL_UNSIGNED_INT:
+ return SWIZZLESHADER_CUBE_UINT;
+ case GL_INT:
+ return SWIZZLESHADER_CUBE_INT;
+ default:
+ UNREACHABLE();
+ return SWIZZLESHADER_INVALID;
+ }
+ case D3D11_SRV_DIMENSION_TEXTURE3D:
+ switch (type)
+ {
+ case GL_FLOAT:
+ return SWIZZLESHADER_3D_FLOAT;
+ case GL_UNSIGNED_INT:
+ return SWIZZLESHADER_3D_UINT;
+ case GL_INT:
+ return SWIZZLESHADER_3D_INT;
+ default:
+ UNREACHABLE();
+ return SWIZZLESHADER_INVALID;
+ }
+ case D3D11_SRV_DIMENSION_TEXTURE2DARRAY:
+ switch (type)
+ {
+ case GL_FLOAT:
+ return SWIZZLESHADER_ARRAY_FLOAT;
+ case GL_UNSIGNED_INT:
+ return SWIZZLESHADER_ARRAY_UINT;
+ case GL_INT:
+ return SWIZZLESHADER_ARRAY_INT;
+ default:
+ UNREACHABLE();
+ return SWIZZLESHADER_INVALID;
+ }
+ default:
UNREACHABLE();
return SWIZZLESHADER_INVALID;
- }
- default:
- UNREACHABLE();
- return SWIZZLESHADER_INVALID;
}
}
-Blit11::ShaderSupport Blit11::getShaderSupport(const Shader &shader)
+gl::Error Blit11::getShaderSupport(const Shader &shader, Blit11::ShaderSupport *supportOut)
{
- ID3D11Device *device = mRenderer->getDevice();
- ShaderSupport support;
-
if (shader.dimension == SHADER_2D)
{
- support.inputLayout = mQuad2DIL.resolve(device);
- support.vertexShader = mQuad2DVS.resolve(device);
- support.geometryShader = nullptr;
- support.vertexWriteFunction = Write2DVertices;
+ ANGLE_TRY(mQuad2DIL.resolve(mRenderer));
+ ANGLE_TRY(mQuad2DVS.resolve(mRenderer));
+ supportOut->inputLayout = &mQuad2DIL.getObj();
+ supportOut->vertexShader = &mQuad2DVS.getObj();
+ supportOut->geometryShader = nullptr;
+ supportOut->vertexWriteFunction = Write2DVertices;
}
else
{
ASSERT(shader.dimension == SHADER_3D);
- support.inputLayout = mQuad3DIL.resolve(device);
- support.vertexShader = mQuad3DVS.resolve(device);
- support.geometryShader = mQuad3DGS.resolve(device);
- support.vertexWriteFunction = Write3DVertices;
+ ANGLE_TRY(mQuad3DIL.resolve(mRenderer));
+ ANGLE_TRY(mQuad3DVS.resolve(mRenderer));
+ ANGLE_TRY(mQuad3DGS.resolve(mRenderer));
+ supportOut->inputLayout = &mQuad2DIL.getObj();
+ supportOut->vertexShader = &mQuad3DVS.getObj();
+ supportOut->geometryShader = &mQuad3DGS.getObj();
+ supportOut->vertexWriteFunction = Write3DVertices;
}
- return support;
+ return gl::NoError();
}
-gl::Error Blit11::swizzleTexture(ID3D11ShaderResourceView *source,
- ID3D11RenderTargetView *dest,
+gl::Error Blit11::swizzleTexture(const gl::Context *context,
+ const d3d11::SharedSRV &source,
+ const d3d11::RenderTargetView &dest,
const gl::Extents &size,
- GLenum swizzleRed,
- GLenum swizzleGreen,
- GLenum swizzleBlue,
- GLenum swizzleAlpha)
+ const gl::SwizzleState &swizzleTarget)
{
- gl::Error error = initResources();
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(initResources());
HRESULT result;
ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
D3D11_SHADER_RESOURCE_VIEW_DESC sourceSRVDesc;
- source->GetDesc(&sourceSRVDesc);
+ source.get()->GetDesc(&sourceSRVDesc);
- const d3d11::DXGIFormat &dxgiFormatInfo = d3d11::GetDXGIFormatInfo(sourceSRVDesc.Format);
- const gl::InternalFormat &sourceFormatInfo = gl::GetInternalFormatInfo(dxgiFormatInfo.internalFormat);
+ GLenum componentType = d3d11::GetComponentType(sourceSRVDesc.Format);
+ if (componentType == GL_NONE)
+ {
+ // We're swizzling the depth component of a depth-stencil texture.
+ switch (sourceSRVDesc.Format)
+ {
+ case DXGI_FORMAT_R24_UNORM_X8_TYPELESS:
+ componentType = GL_UNSIGNED_NORMALIZED;
+ break;
+ case DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS:
+ componentType = GL_FLOAT;
+ break;
+ default:
+ UNREACHABLE();
+ break;
+ }
+ }
GLenum shaderType = GL_NONE;
- switch (sourceFormatInfo.componentType)
+ switch (componentType)
{
- case GL_UNSIGNED_NORMALIZED:
- case GL_SIGNED_NORMALIZED:
- case GL_FLOAT:
- shaderType = GL_FLOAT;
- break;
- case GL_INT:
- shaderType = GL_INT;
- break;
- case GL_UNSIGNED_INT:
- shaderType = GL_UNSIGNED_INT;
- break;
- default:
- UNREACHABLE();
- break;
+ case GL_UNSIGNED_NORMALIZED:
+ case GL_SIGNED_NORMALIZED:
+ case GL_FLOAT:
+ shaderType = GL_FLOAT;
+ break;
+ case GL_INT:
+ shaderType = GL_INT;
+ break;
+ case GL_UNSIGNED_INT:
+ shaderType = GL_UNSIGNED_INT;
+ break;
+ default:
+ UNREACHABLE();
+ break;
}
const Shader *shader = nullptr;
- error = getSwizzleShader(shaderType, sourceSRVDesc.ViewDimension, &shader);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(getSwizzleShader(shaderType, sourceSRVDesc.ViewDimension, &shader));
// Set vertices
D3D11_MAPPED_SUBRESOURCE mappedResource;
- result = deviceContext->Map(mVertexBuffer, 0, D3D11_MAP_WRITE_DISCARD, 0, &mappedResource);
+ result =
+ deviceContext->Map(mVertexBuffer.get(), 0, D3D11_MAP_WRITE_DISCARD, 0, &mappedResource);
if (FAILED(result))
{
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to map internal vertex buffer for swizzle, HRESULT: 0x%X.", result);
+ return gl::OutOfMemory() << "Failed to map internal vertex buffer for swizzle, "
+ << gl::FmtHR(result);
}
- const ShaderSupport &support = getShaderSupport(*shader);
+ ShaderSupport support;
+ ANGLE_TRY(getShaderSupport(*shader, &support));
- UINT stride = 0;
- UINT startIdx = 0;
+ UINT stride = 0;
UINT drawCount = 0;
D3D11_PRIMITIVE_TOPOLOGY topology;
gl::Box area(0, 0, 0, size.width, size.height, size.depth);
- support.vertexWriteFunction(area, size, area, size, mappedResource.pData, &stride, &drawCount, &topology);
+ support.vertexWriteFunction(area, size, area, size, mappedResource.pData, &stride, &drawCount,
+ &topology);
- deviceContext->Unmap(mVertexBuffer, 0);
+ deviceContext->Unmap(mVertexBuffer.get(), 0);
// Set constant buffer
- result = deviceContext->Map(mSwizzleCB, 0, D3D11_MAP_WRITE_DISCARD, 0, &mappedResource);
+ result = deviceContext->Map(mSwizzleCB.get(), 0, D3D11_MAP_WRITE_DISCARD, 0, &mappedResource);
if (FAILED(result))
{
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to map internal constant buffer for swizzle, HRESULT: 0x%X.", result);
+ return gl::OutOfMemory() << "Failed to map internal constant buffer for swizzle, "
+ << gl::FmtHR(result);
}
- unsigned int *swizzleIndices = reinterpret_cast<unsigned int*>(mappedResource.pData);
- swizzleIndices[0] = GetSwizzleIndex(swizzleRed);
- swizzleIndices[1] = GetSwizzleIndex(swizzleGreen);
- swizzleIndices[2] = GetSwizzleIndex(swizzleBlue);
- swizzleIndices[3] = GetSwizzleIndex(swizzleAlpha);
+ unsigned int *swizzleIndices = reinterpret_cast<unsigned int *>(mappedResource.pData);
+ swizzleIndices[0] = GetSwizzleIndex(swizzleTarget.swizzleRed);
+ swizzleIndices[1] = GetSwizzleIndex(swizzleTarget.swizzleGreen);
+ swizzleIndices[2] = GetSwizzleIndex(swizzleTarget.swizzleBlue);
+ swizzleIndices[3] = GetSwizzleIndex(swizzleTarget.swizzleAlpha);
- deviceContext->Unmap(mSwizzleCB, 0);
+ deviceContext->Unmap(mSwizzleCB.get(), 0);
+
+ StateManager11 *stateManager = mRenderer->getStateManager();
// Apply vertex buffer
- deviceContext->IASetVertexBuffers(0, 1, &mVertexBuffer, &stride, &startIdx);
+ stateManager->setSingleVertexBuffer(&mVertexBuffer, stride, 0);
// Apply constant buffer
- deviceContext->PSSetConstantBuffers(0, 1, &mSwizzleCB);
+ stateManager->setPixelConstantBuffer(0, &mSwizzleCB);
// Apply state
- deviceContext->OMSetBlendState(nullptr, nullptr, 0xFFFFFFF);
- deviceContext->OMSetDepthStencilState(nullptr, 0xFFFFFFFF);
- deviceContext->RSSetState(mScissorDisabledRasterizerState);
+ stateManager->setSimpleBlendState(nullptr);
+ stateManager->setDepthStencilState(nullptr, 0xFFFFFFFF);
+ stateManager->setRasterizerState(&mScissorDisabledRasterizerState);
// Apply shaders
- deviceContext->IASetInputLayout(support.inputLayout);
- deviceContext->IASetPrimitiveTopology(topology);
- deviceContext->VSSetShader(support.vertexShader, nullptr, 0);
-
- deviceContext->PSSetShader(shader->pixelShader, nullptr, 0);
- deviceContext->GSSetShader(support.geometryShader, nullptr, 0);
+ stateManager->setInputLayout(support.inputLayout);
+ stateManager->setPrimitiveTopology(topology);
- // Unset the currently bound shader resource to avoid conflicts
- auto stateManager = mRenderer->getStateManager();
- stateManager->setShaderResource(gl::SAMPLER_PIXEL, 0, nullptr);
+ stateManager->setDrawShaders(support.vertexShader, support.geometryShader,
+ &shader->pixelShader);
// Apply render target
- mRenderer->setOneTimeRenderTarget(dest);
+ stateManager->setRenderTarget(dest.get(), nullptr);
// Set the viewport
- D3D11_VIEWPORT viewport;
- viewport.TopLeftX = 0;
- viewport.TopLeftY = 0;
- viewport.Width = static_cast<FLOAT>(size.width);
- viewport.Height = static_cast<FLOAT>(size.height);
- viewport.MinDepth = 0.0f;
- viewport.MaxDepth = 1.0f;
- deviceContext->RSSetViewports(1, &viewport);
-
- // Apply textures
- stateManager->setShaderResource(gl::SAMPLER_PIXEL, 0, source);
+ stateManager->setSimpleViewport(size);
- // Apply samplers
- deviceContext->PSSetSamplers(0, 1, &mPointSampler);
+ // Apply textures and sampler
+ stateManager->setSimplePixelTextureAndSampler(source, mPointSampler);
// Draw the quad
deviceContext->Draw(drawCount, 0);
- // Unbind textures and render targets and vertex buffer
- stateManager->setShaderResource(gl::SAMPLER_PIXEL, 0, nullptr);
-
- mRenderer->unapplyRenderTargets();
-
- UINT zero = 0;
- ID3D11Buffer *const nullBuffer = nullptr;
- deviceContext->IASetVertexBuffers(0, 1, &nullBuffer, &zero, &zero);
-
- mRenderer->markAllStateDirty();
-
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error Blit11::copyTexture(ID3D11ShaderResourceView *source,
+gl::Error Blit11::copyTexture(const gl::Context *context,
+ const d3d11::SharedSRV &source,
const gl::Box &sourceArea,
const gl::Extents &sourceSize,
- ID3D11RenderTargetView *dest,
+ GLenum sourceFormat,
+ const d3d11::RenderTargetView &dest,
const gl::Box &destArea,
const gl::Extents &destSize,
const gl::Rectangle *scissor,
GLenum destFormat,
GLenum filter,
- bool maskOffAlpha)
+ bool maskOffAlpha,
+ bool unpackPremultiplyAlpha,
+ bool unpackUnmultiplyAlpha)
{
- gl::Error error = initResources();
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(initResources());
HRESULT result;
ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
@@ -771,635 +1145,1009 @@ gl::Error Blit11::copyTexture(ID3D11ShaderResourceView *source,
// Determine if the source format is a signed integer format, the destFormat will already
// be GL_XXXX_INTEGER but it does not tell us if it is signed or unsigned.
D3D11_SHADER_RESOURCE_VIEW_DESC sourceSRVDesc;
- source->GetDesc(&sourceSRVDesc);
+ source.get()->GetDesc(&sourceSRVDesc);
+
+ GLenum componentType = d3d11::GetComponentType(sourceSRVDesc.Format);
- const d3d11::DXGIFormat &dxgiFormatInfo = d3d11::GetDXGIFormatInfo(sourceSRVDesc.Format);
- const gl::InternalFormat &internalFormatInfo = gl::GetInternalFormatInfo(dxgiFormatInfo.internalFormat);
+ ASSERT(componentType != GL_NONE);
+ ASSERT(componentType != GL_SIGNED_NORMALIZED);
+ bool isSigned = (componentType == GL_INT);
- bool isSigned = (internalFormatInfo.componentType == GL_INT);
- ShaderDimension dimension = (sourceSRVDesc.ViewDimension == D3D11_SRV_DIMENSION_TEXTURE3D) ? SHADER_3D : SHADER_2D;
+ ShaderDimension dimension =
+ (sourceSRVDesc.ViewDimension == D3D11_SRV_DIMENSION_TEXTURE3D) ? SHADER_3D : SHADER_2D;
const Shader *shader = nullptr;
- error = getBlitShader(destFormat, isSigned, dimension, &shader);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(getBlitShader(destFormat, sourceFormat, isSigned, unpackPremultiplyAlpha,
+ unpackUnmultiplyAlpha, dimension, &shader));
- const ShaderSupport &support = getShaderSupport(*shader);
+ ShaderSupport support;
+ ANGLE_TRY(getShaderSupport(*shader, &support));
// Set vertices
D3D11_MAPPED_SUBRESOURCE mappedResource;
- result = deviceContext->Map(mVertexBuffer, 0, D3D11_MAP_WRITE_DISCARD, 0, &mappedResource);
+ result =
+ deviceContext->Map(mVertexBuffer.get(), 0, D3D11_MAP_WRITE_DISCARD, 0, &mappedResource);
if (FAILED(result))
{
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to map internal vertex buffer for texture copy, HRESULT: 0x%X.", result);
+ return gl::OutOfMemory() << "Failed to map internal vertex buffer for texture copy, "
+ << gl::FmtHR(result);
}
- UINT stride = 0;
- UINT startIdx = 0;
+ UINT stride = 0;
UINT drawCount = 0;
D3D11_PRIMITIVE_TOPOLOGY topology;
support.vertexWriteFunction(sourceArea, sourceSize, destArea, destSize, mappedResource.pData,
&stride, &drawCount, &topology);
- deviceContext->Unmap(mVertexBuffer, 0);
+ deviceContext->Unmap(mVertexBuffer.get(), 0);
+
+ StateManager11 *stateManager = mRenderer->getStateManager();
// Apply vertex buffer
- deviceContext->IASetVertexBuffers(0, 1, &mVertexBuffer, &stride, &startIdx);
+ stateManager->setSingleVertexBuffer(&mVertexBuffer, stride, 0);
// Apply state
if (maskOffAlpha)
{
- ID3D11BlendState *blendState = mAlphaMaskBlendState.resolve(mRenderer->getDevice());
- ASSERT(blendState);
- deviceContext->OMSetBlendState(blendState, nullptr, 0xFFFFFFF);
+ ANGLE_TRY(mAlphaMaskBlendState.resolve(mRenderer));
+ stateManager->setSimpleBlendState(&mAlphaMaskBlendState.getObj());
}
else
{
- deviceContext->OMSetBlendState(nullptr, nullptr, 0xFFFFFFF);
+ stateManager->setSimpleBlendState(nullptr);
}
- deviceContext->OMSetDepthStencilState(nullptr, 0xFFFFFFFF);
+ stateManager->setDepthStencilState(nullptr, 0xFFFFFFFF);
if (scissor)
{
- D3D11_RECT scissorRect;
- scissorRect.left = scissor->x;
- scissorRect.right = scissor->x + scissor->width;
- scissorRect.top = scissor->y;
- scissorRect.bottom = scissor->y + scissor->height;
-
- deviceContext->RSSetScissorRects(1, &scissorRect);
- deviceContext->RSSetState(mScissorEnabledRasterizerState);
+ stateManager->setSimpleScissorRect(*scissor);
+ stateManager->setRasterizerState(&mScissorEnabledRasterizerState);
}
else
{
- deviceContext->RSSetState(mScissorDisabledRasterizerState);
+ stateManager->setRasterizerState(&mScissorDisabledRasterizerState);
}
// Apply shaders
- deviceContext->IASetInputLayout(support.inputLayout);
- deviceContext->IASetPrimitiveTopology(topology);
- deviceContext->VSSetShader(support.vertexShader, nullptr, 0);
-
- deviceContext->PSSetShader(shader->pixelShader, nullptr, 0);
- deviceContext->GSSetShader(support.geometryShader, nullptr, 0);
+ stateManager->setInputLayout(support.inputLayout);
+ stateManager->setPrimitiveTopology(topology);
- // Unset the currently bound shader resource to avoid conflicts
- auto stateManager = mRenderer->getStateManager();
- stateManager->setShaderResource(gl::SAMPLER_PIXEL, 0, nullptr);
+ stateManager->setDrawShaders(support.vertexShader, support.geometryShader,
+ &shader->pixelShader);
// Apply render target
- mRenderer->setOneTimeRenderTarget(dest);
+ stateManager->setRenderTarget(dest.get(), nullptr);
// Set the viewport
- D3D11_VIEWPORT viewport;
- viewport.TopLeftX = 0;
- viewport.TopLeftY = 0;
- viewport.Width = static_cast<FLOAT>(destSize.width);
- viewport.Height = static_cast<FLOAT>(destSize.height);
- viewport.MinDepth = 0.0f;
- viewport.MaxDepth = 1.0f;
- deviceContext->RSSetViewports(1, &viewport);
-
- // Apply textures
- stateManager->setShaderResource(gl::SAMPLER_PIXEL, 0, source);
-
- // Apply samplers
- ID3D11SamplerState *sampler = nullptr;
+ stateManager->setSimpleViewport(destSize);
+
+ // Apply texture and sampler
switch (filter)
{
- case GL_NEAREST: sampler = mPointSampler; break;
- case GL_LINEAR: sampler = mLinearSampler; break;
-
- default:
- UNREACHABLE();
- return gl::Error(GL_OUT_OF_MEMORY, "Internal error, unknown blit filter mode.");
+ case GL_NEAREST:
+ stateManager->setSimplePixelTextureAndSampler(source, mPointSampler);
+ break;
+ case GL_LINEAR:
+ stateManager->setSimplePixelTextureAndSampler(source, mLinearSampler);
+ break;
+
+ default:
+ UNREACHABLE();
+ return gl::InternalError() << "Internal error, unknown blit filter mode.";
}
- deviceContext->PSSetSamplers(0, 1, &sampler);
// Draw the quad
deviceContext->Draw(drawCount, 0);
- // Unbind textures and render targets and vertex buffer
- stateManager->setShaderResource(gl::SAMPLER_PIXEL, 0, nullptr);
-
- mRenderer->unapplyRenderTargets();
-
- UINT zero = 0;
- ID3D11Buffer *const nullBuffer = nullptr;
- deviceContext->IASetVertexBuffers(0, 1, &nullBuffer, &zero, &zero);
-
- mRenderer->markAllStateDirty();
-
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error Blit11::copyStencil(ID3D11Resource *source, unsigned int sourceSubresource, const gl::Box &sourceArea, const gl::Extents &sourceSize,
- ID3D11Resource *dest, unsigned int destSubresource, const gl::Box &destArea, const gl::Extents &destSize,
+gl::Error Blit11::copyStencil(const gl::Context *context,
+ const TextureHelper11 &source,
+ unsigned int sourceSubresource,
+ const gl::Box &sourceArea,
+ const gl::Extents &sourceSize,
+ const TextureHelper11 &dest,
+ unsigned int destSubresource,
+ const gl::Box &destArea,
+ const gl::Extents &destSize,
const gl::Rectangle *scissor)
{
- return copyDepthStencil(source, sourceSubresource, sourceArea, sourceSize,
- dest, destSubresource, destArea, destSize,
- scissor, true);
+ return copyDepthStencilImpl(source, sourceSubresource, sourceArea, sourceSize, dest,
+ destSubresource, destArea, destSize, scissor, true);
}
-gl::Error Blit11::copyDepth(ID3D11ShaderResourceView *source, const gl::Box &sourceArea, const gl::Extents &sourceSize,
- ID3D11DepthStencilView *dest, const gl::Box &destArea, const gl::Extents &destSize,
+gl::Error Blit11::copyDepth(const gl::Context *context,
+ const d3d11::SharedSRV &source,
+ const gl::Box &sourceArea,
+ const gl::Extents &sourceSize,
+ const d3d11::DepthStencilView &dest,
+ const gl::Box &destArea,
+ const gl::Extents &destSize,
const gl::Rectangle *scissor)
{
- gl::Error error = initResources();
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(initResources());
HRESULT result;
ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
// Set vertices
D3D11_MAPPED_SUBRESOURCE mappedResource;
- result = deviceContext->Map(mVertexBuffer, 0, D3D11_MAP_WRITE_DISCARD, 0, &mappedResource);
+ result =
+ deviceContext->Map(mVertexBuffer.get(), 0, D3D11_MAP_WRITE_DISCARD, 0, &mappedResource);
if (FAILED(result))
{
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to map internal vertex buffer for texture copy, HRESULT: 0x%X.", result);
+ return gl::OutOfMemory() << "Failed to map internal vertex buffer for texture copy, "
+ << gl::FmtHR(result);
}
- UINT stride = 0;
- UINT startIdx = 0;
+ UINT stride = 0;
UINT drawCount = 0;
D3D11_PRIMITIVE_TOPOLOGY topology;
- Write2DVertices(sourceArea, sourceSize, destArea, destSize, mappedResource.pData,
- &stride, &drawCount, &topology);
+ Write2DVertices(sourceArea, sourceSize, destArea, destSize, mappedResource.pData, &stride,
+ &drawCount, &topology);
- deviceContext->Unmap(mVertexBuffer, 0);
+ deviceContext->Unmap(mVertexBuffer.get(), 0);
+
+ StateManager11 *stateManager = mRenderer->getStateManager();
// Apply vertex buffer
- deviceContext->IASetVertexBuffers(0, 1, &mVertexBuffer, &stride, &startIdx);
+ stateManager->setSingleVertexBuffer(&mVertexBuffer, stride, 0);
// Apply state
- deviceContext->OMSetBlendState(nullptr, nullptr, 0xFFFFFFF);
- deviceContext->OMSetDepthStencilState(mDepthStencilState, 0xFFFFFFFF);
+ stateManager->setSimpleBlendState(nullptr);
+ stateManager->setDepthStencilState(&mDepthStencilState, 0xFFFFFFFF);
if (scissor)
{
- D3D11_RECT scissorRect;
- scissorRect.left = scissor->x;
- scissorRect.right = scissor->x + scissor->width;
- scissorRect.top = scissor->y;
- scissorRect.bottom = scissor->y + scissor->height;
-
- deviceContext->RSSetScissorRects(1, &scissorRect);
- deviceContext->RSSetState(mScissorEnabledRasterizerState);
+ stateManager->setSimpleScissorRect(*scissor);
+ stateManager->setRasterizerState(&mScissorEnabledRasterizerState);
}
else
{
- deviceContext->RSSetState(mScissorDisabledRasterizerState);
+ stateManager->setRasterizerState(&mScissorDisabledRasterizerState);
}
- ID3D11Device *device = mRenderer->getDevice();
- ID3D11VertexShader *quad2DVS = mQuad2DVS.resolve(device);
- if (quad2DVS == nullptr)
- {
- return gl::Error(GL_INVALID_OPERATION, "Error compiling internal 2D blit vertex shader");
- }
+ ANGLE_TRY(mQuad2DIL.resolve(mRenderer));
+ ANGLE_TRY(mQuad2DVS.resolve(mRenderer));
+ ANGLE_TRY(mDepthPS.resolve(mRenderer));
// Apply shaders
- deviceContext->IASetInputLayout(mQuad2DIL.resolve(device));
- deviceContext->IASetPrimitiveTopology(topology);
- deviceContext->VSSetShader(quad2DVS, nullptr, 0);
+ stateManager->setInputLayout(&mQuad2DIL.getObj());
+ stateManager->setPrimitiveTopology(topology);
- deviceContext->PSSetShader(mDepthPS.resolve(device), nullptr, 0);
- deviceContext->GSSetShader(nullptr, nullptr, 0);
-
- // Unset the currently bound shader resource to avoid conflicts
- auto stateManager = mRenderer->getStateManager();
- stateManager->setShaderResource(gl::SAMPLER_PIXEL, 0, nullptr);
+ stateManager->setDrawShaders(&mQuad2DVS.getObj(), nullptr, &mDepthPS.getObj());
// Apply render target
- deviceContext->OMSetRenderTargets(0, nullptr, dest);
+ stateManager->setRenderTarget(nullptr, dest.get());
// Set the viewport
- D3D11_VIEWPORT viewport;
- viewport.TopLeftX = 0;
- viewport.TopLeftY = 0;
- viewport.Width = static_cast<FLOAT>(destSize.width);
- viewport.Height = static_cast<FLOAT>(destSize.height);
- viewport.MinDepth = 0.0f;
- viewport.MaxDepth = 1.0f;
- deviceContext->RSSetViewports(1, &viewport);
-
- // Apply textures
- stateManager->setShaderResource(gl::SAMPLER_PIXEL, 0, source);
+ stateManager->setSimpleViewport(destSize);
- // Apply samplers
- deviceContext->PSSetSamplers(0, 1, &mPointSampler);
+ // Apply texture and sampler
+ stateManager->setSimplePixelTextureAndSampler(source, mPointSampler);
// Draw the quad
deviceContext->Draw(drawCount, 0);
- // Unbind textures and render targets and vertex buffer
- stateManager->setShaderResource(gl::SAMPLER_PIXEL, 0, nullptr);
-
- mRenderer->unapplyRenderTargets();
-
- UINT zero = 0;
- ID3D11Buffer *const nullBuffer = nullptr;
- deviceContext->IASetVertexBuffers(0, 1, &nullBuffer, &zero, &zero);
-
- mRenderer->markAllStateDirty();
-
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error Blit11::copyDepthStencil(ID3D11Resource *source, unsigned int sourceSubresource, const gl::Box &sourceArea, const gl::Extents &sourceSize,
- ID3D11Resource *dest, unsigned int destSubresource, const gl::Box &destArea, const gl::Extents &destSize,
+gl::Error Blit11::copyDepthStencil(const TextureHelper11 &source,
+ unsigned int sourceSubresource,
+ const gl::Box &sourceArea,
+ const gl::Extents &sourceSize,
+ const TextureHelper11 &dest,
+ unsigned int destSubresource,
+ const gl::Box &destArea,
+ const gl::Extents &destSize,
const gl::Rectangle *scissor)
{
- return copyDepthStencil(source, sourceSubresource, sourceArea, sourceSize,
- dest, destSubresource, destArea, destSize,
- scissor, false);
+ return copyDepthStencilImpl(source, sourceSubresource, sourceArea, sourceSize, dest,
+ destSubresource, destArea, destSize, scissor, false);
}
-gl::Error Blit11::copyDepthStencil(ID3D11Resource *source, unsigned int sourceSubresource, const gl::Box &sourceArea, const gl::Extents &sourceSize,
- ID3D11Resource *dest, unsigned int destSubresource, const gl::Box &destArea, const gl::Extents &destSize,
- const gl::Rectangle *scissor, bool stencilOnly)
+gl::Error Blit11::copyDepthStencilImpl(const TextureHelper11 &source,
+ unsigned int sourceSubresource,
+ const gl::Box &sourceArea,
+ const gl::Extents &sourceSize,
+ const TextureHelper11 &dest,
+ unsigned int destSubresource,
+ const gl::Box &destArea,
+ const gl::Extents &destSize,
+ const gl::Rectangle *scissor,
+ bool stencilOnly)
{
- gl::Error error = initResources();
- if (error.isError())
- {
- return error;
- }
+ auto srcDXGIFormat = source.getFormat();
+ const auto &srcSizeInfo = d3d11::GetDXGIFormatSizeInfo(srcDXGIFormat);
+ unsigned int srcPixelSize = srcSizeInfo.pixelBytes;
+ unsigned int copyOffset = 0;
+ unsigned int copySize = srcPixelSize;
+ auto destDXGIFormat = dest.getFormat();
+ const auto &destSizeInfo = d3d11::GetDXGIFormatSizeInfo(destDXGIFormat);
+ unsigned int destPixelSize = destSizeInfo.pixelBytes;
- ID3D11Device *device = mRenderer->getDevice();
- ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
+ ASSERT(srcDXGIFormat == destDXGIFormat || destDXGIFormat == DXGI_FORMAT_R32_TYPELESS);
- ID3D11Resource *sourceStaging = CreateStagingTexture(device, deviceContext, source, sourceSubresource, sourceSize, D3D11_CPU_ACCESS_READ);
- // HACK: Create the destination staging buffer as a read/write texture so ID3D11DevicContext::UpdateSubresource can be called
- // using it's mapped data as a source
- ID3D11Resource *destStaging = CreateStagingTexture(device, deviceContext, dest, destSubresource, destSize, D3D11_CPU_ACCESS_READ | D3D11_CPU_ACCESS_WRITE);
+ if (stencilOnly)
+ {
+ const auto &srcFormat = source.getFormatSet().format();
+
+ // Stencil channel should be right after the depth channel. Some views to depth/stencil
+ // resources have red channel for depth, in which case the depth channel bit width is in
+ // redBits.
+ ASSERT((srcFormat.redBits != 0) != (srcFormat.depthBits != 0));
+ GLuint depthBits = srcFormat.redBits + srcFormat.depthBits;
+ // Known formats have either 24 or 32 bits of depth.
+ ASSERT(depthBits == 24 || depthBits == 32);
+ copyOffset = depthBits / 8;
+
+ // Stencil is assumed to be 8-bit - currently this is true for all possible formats.
+ copySize = 1;
+ }
- if (!sourceStaging || !destStaging)
+ if (srcDXGIFormat != destDXGIFormat)
{
- SafeRelease(sourceStaging);
- SafeRelease(destStaging);
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal staging textures for depth stencil blit.");
+ if (srcDXGIFormat == DXGI_FORMAT_R24G8_TYPELESS)
+ {
+ ASSERT(sourceArea == destArea && sourceSize == destSize && scissor == nullptr);
+ return copyAndConvert(source, sourceSubresource, sourceArea, sourceSize, dest,
+ destSubresource, destArea, destSize, scissor, copyOffset,
+ copyOffset, copySize, srcPixelSize, destPixelSize,
+ BlitD24S8ToD32F);
+ }
+ ASSERT(srcDXGIFormat == DXGI_FORMAT_R32G8X24_TYPELESS);
+ return copyAndConvert(source, sourceSubresource, sourceArea, sourceSize, dest,
+ destSubresource, destArea, destSize, scissor, copyOffset, copyOffset,
+ copySize, srcPixelSize, destPixelSize, BlitD32FS8ToD32F);
}
- DXGI_FORMAT format = GetTextureFormat(source);
- ASSERT(format == GetTextureFormat(dest));
+ return copyAndConvert(source, sourceSubresource, sourceArea, sourceSize, dest, destSubresource,
+ destArea, destSize, scissor, copyOffset, copyOffset, copySize,
+ srcPixelSize, destPixelSize, StretchedBlitNearest);
+}
- const d3d11::DXGIFormat &dxgiFormatInfo = d3d11::GetDXGIFormatInfo(format);
- unsigned int pixelSize = dxgiFormatInfo.pixelBytes;
- unsigned int copyOffset = 0;
- unsigned int copySize = pixelSize;
- if (stencilOnly)
- {
- copyOffset = dxgiFormatInfo.depthBits / 8;
- copySize = dxgiFormatInfo.stencilBits / 8;
+gl::Error Blit11::copyAndConvertImpl(const TextureHelper11 &source,
+ unsigned int sourceSubresource,
+ const gl::Box &sourceArea,
+ const gl::Extents &sourceSize,
+ const TextureHelper11 &destStaging,
+ const gl::Box &destArea,
+ const gl::Extents &destSize,
+ const gl::Rectangle *scissor,
+ size_t readOffset,
+ size_t writeOffset,
+ size_t copySize,
+ size_t srcPixelStride,
+ size_t destPixelStride,
+ BlitConvertFunction *convertFunction)
+{
+ ANGLE_TRY(initResources());
- // It would be expensive to have non-byte sized stencil sizes since it would
- // require reading from the destination, currently there aren't any though.
- ASSERT(dxgiFormatInfo.stencilBits % 8 == 0 &&
- dxgiFormatInfo.depthBits % 8 == 0);
- }
+ ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
+
+ TextureHelper11 sourceStaging;
+ ANGLE_TRY_RESULT(mRenderer->createStagingTexture(ResourceType::Texture2D, source.getFormatSet(),
+ sourceSize, StagingAccess::READ),
+ sourceStaging);
+
+ deviceContext->CopySubresourceRegion(sourceStaging.get(), 0, 0, 0, 0, source.get(),
+ sourceSubresource, nullptr);
D3D11_MAPPED_SUBRESOURCE sourceMapping;
- HRESULT result = deviceContext->Map(sourceStaging, 0, D3D11_MAP_READ, 0, &sourceMapping);
+ HRESULT result = deviceContext->Map(sourceStaging.get(), 0, D3D11_MAP_READ, 0, &sourceMapping);
if (FAILED(result))
{
- SafeRelease(sourceStaging);
- SafeRelease(destStaging);
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to map internal source staging texture for depth stencil blit, HRESULT: 0x%X.", result);
+ return gl::OutOfMemory()
+ << "Failed to map internal source staging texture for depth stencil blit, "
+ << gl::FmtHR(result);
}
D3D11_MAPPED_SUBRESOURCE destMapping;
- result = deviceContext->Map(destStaging, 0, D3D11_MAP_WRITE, 0, &destMapping);
+ result = deviceContext->Map(destStaging.get(), 0, D3D11_MAP_WRITE, 0, &destMapping);
if (FAILED(result))
{
- deviceContext->Unmap(sourceStaging, 0);
- SafeRelease(sourceStaging);
- SafeRelease(destStaging);
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to map internal destination staging texture for depth stencil blit, HRESULT: 0x%X.", result);
+ deviceContext->Unmap(sourceStaging.get(), 0);
+ return gl::OutOfMemory()
+ << "Failed to map internal destination staging texture for depth stencil blit, "
+ << gl::FmtHR(result);
}
- gl::Rectangle clippedDestArea(destArea.x, destArea.y, destArea.width, destArea.height);
-
// Clip dest area to the destination size
- gl::ClipRectangle(clippedDestArea, gl::Rectangle(0, 0, destSize.width, destSize.height), &clippedDestArea);
+ gl::Rectangle clipRect = gl::Rectangle(0, 0, destSize.width, destSize.height);
// Clip dest area to the scissor
if (scissor)
{
- gl::ClipRectangle(clippedDestArea, *scissor, &clippedDestArea);
+ gl::ClipRectangle(clipRect, *scissor, &clipRect);
}
- // Determine if entire rows can be copied at once instead of each individual pixel, requires that there is
- // no out of bounds lookups required, the entire pixel is copied and no stretching
- bool wholeRowCopy = sourceArea.width == clippedDestArea.width &&
- sourceArea.x >= 0 && sourceArea.x + sourceArea.width <= sourceSize.width &&
- copySize == pixelSize;
+ convertFunction(sourceArea, destArea, clipRect, sourceSize, sourceMapping.RowPitch,
+ destMapping.RowPitch, readOffset, writeOffset, copySize, srcPixelStride,
+ destPixelStride, static_cast<const uint8_t *>(sourceMapping.pData),
+ static_cast<uint8_t *>(destMapping.pData));
- for (int y = clippedDestArea.y; y < clippedDestArea.y + clippedDestArea.height; y++)
- {
- float yPerc = static_cast<float>(y - destArea.y) / (destArea.height - 1);
+ deviceContext->Unmap(sourceStaging.get(), 0);
+ deviceContext->Unmap(destStaging.get(), 0);
- // Interpolate using the original source rectangle to determine which row to sample from while clamping to the edges
- unsigned int readRow = static_cast<unsigned int>(gl::clamp(sourceArea.y + floor(yPerc * (sourceArea.height - 1) + 0.5f), 0, sourceSize.height - 1));
- unsigned int writeRow = y;
-
- if (wholeRowCopy)
- {
- void *sourceRow = reinterpret_cast<char*>(sourceMapping.pData) +
- readRow * sourceMapping.RowPitch +
- sourceArea.x * pixelSize;
+ return gl::NoError();
+}
- void *destRow = reinterpret_cast<char*>(destMapping.pData) +
- writeRow * destMapping.RowPitch +
- destArea.x * pixelSize;
+gl::Error Blit11::copyAndConvert(const TextureHelper11 &source,
+ unsigned int sourceSubresource,
+ const gl::Box &sourceArea,
+ const gl::Extents &sourceSize,
+ const TextureHelper11 &dest,
+ unsigned int destSubresource,
+ const gl::Box &destArea,
+ const gl::Extents &destSize,
+ const gl::Rectangle *scissor,
+ size_t readOffset,
+ size_t writeOffset,
+ size_t copySize,
+ size_t srcPixelStride,
+ size_t destPixelStride,
+ BlitConvertFunction *convertFunction)
+{
+ ANGLE_TRY(initResources());
- memcpy(destRow, sourceRow, pixelSize * destArea.width);
- }
- else
- {
- for (int x = clippedDestArea.x; x < clippedDestArea.x + clippedDestArea.width; x++)
- {
- float xPerc = static_cast<float>(x - destArea.x) / (destArea.width - 1);
+ ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
- // Interpolate the original source rectangle to determine which column to sample from while clamping to the edges
- unsigned int readColumn = static_cast<unsigned int>(gl::clamp(sourceArea.x + floor(xPerc * (sourceArea.width - 1) + 0.5f), 0, sourceSize.width - 1));
- unsigned int writeColumn = x;
+ // HACK: Create the destination staging buffer as a read/write texture so
+ // ID3D11DevicContext::UpdateSubresource can be called
+ // using it's mapped data as a source
+ TextureHelper11 destStaging;
+ ANGLE_TRY_RESULT(mRenderer->createStagingTexture(ResourceType::Texture2D, dest.getFormatSet(),
+ destSize, StagingAccess::READ_WRITE),
+ destStaging);
- void *sourcePixel = reinterpret_cast<char*>(sourceMapping.pData) +
- readRow * sourceMapping.RowPitch +
- readColumn * pixelSize +
- copyOffset;
+ deviceContext->CopySubresourceRegion(destStaging.get(), 0, 0, 0, 0, dest.get(), destSubresource,
+ nullptr);
- void *destPixel = reinterpret_cast<char*>(destMapping.pData) +
- writeRow * destMapping.RowPitch +
- writeColumn * pixelSize +
- copyOffset;
+ ANGLE_TRY(copyAndConvertImpl(source, sourceSubresource, sourceArea, sourceSize, destStaging,
+ destArea, destSize, scissor, readOffset, writeOffset, copySize,
+ srcPixelStride, destPixelStride, convertFunction));
- memcpy(destPixel, sourcePixel, copySize);
- }
- }
+ // Work around timeouts/TDRs in older NVIDIA drivers.
+ if (mRenderer->getWorkarounds().depthStencilBlitExtraCopy)
+ {
+ D3D11_MAPPED_SUBRESOURCE mapped;
+ deviceContext->Map(destStaging.get(), 0, D3D11_MAP_READ, 0, &mapped);
+ deviceContext->UpdateSubresource(dest.get(), destSubresource, nullptr, mapped.pData,
+ mapped.RowPitch, mapped.DepthPitch);
+ deviceContext->Unmap(destStaging.get(), 0);
+ }
+ else
+ {
+ deviceContext->CopySubresourceRegion(dest.get(), destSubresource, 0, 0, 0,
+ destStaging.get(), 0, nullptr);
}
- // HACK: Use ID3D11DevicContext::UpdateSubresource which causes an extra copy compared to ID3D11DevicContext::CopySubresourceRegion
- // according to MSDN.
- deviceContext->UpdateSubresource(dest, destSubresource, nullptr, destMapping.pData, destMapping.RowPitch, destMapping.DepthPitch);
-
- deviceContext->Unmap(sourceStaging, 0);
- deviceContext->Unmap(destStaging, 0);
-
- // TODO: Determine why this call to ID3D11DevicContext::CopySubresourceRegion causes a TDR timeout on some
- // systems when called repeatedly.
- // deviceContext->CopySubresourceRegion(dest, destSubresource, 0, 0, 0, destStaging, 0, nullptr);
-
- SafeRelease(sourceStaging);
- SafeRelease(destStaging);
-
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-void Blit11::addBlitShaderToMap(BlitShaderType blitShaderType, ShaderDimension dimension, ID3D11PixelShader *ps)
+gl::Error Blit11::addBlitShaderToMap(BlitShaderType blitShaderType,
+ ShaderDimension dimension,
+ const ShaderData &shaderData,
+ const char *name)
{
ASSERT(mBlitShaderMap.find(blitShaderType) == mBlitShaderMap.end());
- ASSERT(ps);
+
+ d3d11::PixelShader ps;
+ ANGLE_TRY(mRenderer->allocateResource(shaderData, &ps));
+ ps.setDebugName(name);
Shader shader;
- shader.dimension = dimension;
- shader.pixelShader = ps;
+ shader.dimension = dimension;
+ shader.pixelShader = std::move(ps);
- mBlitShaderMap[blitShaderType] = shader;
+ mBlitShaderMap[blitShaderType] = std::move(shader);
+ return gl::NoError();
}
-void Blit11::addSwizzleShaderToMap(SwizzleShaderType swizzleShaderType, ShaderDimension dimension, ID3D11PixelShader *ps)
+gl::Error Blit11::addSwizzleShaderToMap(SwizzleShaderType swizzleShaderType,
+ ShaderDimension dimension,
+ const ShaderData &shaderData,
+ const char *name)
{
ASSERT(mSwizzleShaderMap.find(swizzleShaderType) == mSwizzleShaderMap.end());
- ASSERT(ps);
+
+ d3d11::PixelShader ps;
+ ANGLE_TRY(mRenderer->allocateResource(shaderData, &ps));
+ ps.setDebugName(name);
Shader shader;
- shader.dimension = dimension;
- shader.pixelShader = ps;
+ shader.dimension = dimension;
+ shader.pixelShader = std::move(ps);
- mSwizzleShaderMap[swizzleShaderType] = shader;
+ mSwizzleShaderMap[swizzleShaderType] = std::move(shader);
+ return gl::NoError();
}
void Blit11::clearShaderMap()
{
- for (auto &blitShader : mBlitShaderMap)
- {
- SafeRelease(blitShader.second.pixelShader);
- }
mBlitShaderMap.clear();
-
- for (auto &swizzleShader : mSwizzleShaderMap)
- {
- SafeRelease(swizzleShader.second.pixelShader);
- }
mSwizzleShaderMap.clear();
}
-gl::Error Blit11::getBlitShader(GLenum destFormat, bool isSigned, ShaderDimension dimension, const Shader **shader)
+gl::Error Blit11::getBlitShader(GLenum destFormat,
+ GLenum sourceFormat,
+ bool isSigned,
+ bool unpackPremultiplyAlpha,
+ bool unpackUnmultiplyAlpha,
+ ShaderDimension dimension,
+ const Shader **shader)
{
- BlitShaderType blitShaderType = GetBlitShaderType(destFormat, isSigned, dimension);
+ BlitShaderType blitShaderType =
+ GetBlitShaderType(destFormat, sourceFormat, isSigned, unpackPremultiplyAlpha,
+ unpackUnmultiplyAlpha, dimension);
if (blitShaderType == BLITSHADER_INVALID)
{
- return gl::Error(GL_INVALID_OPERATION, "Internal blit shader type mismatch");
+ return gl::InternalError() << "Internal blit shader type mismatch";
}
auto blitShaderIt = mBlitShaderMap.find(blitShaderType);
if (blitShaderIt != mBlitShaderMap.end())
{
*shader = &blitShaderIt->second;
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
ASSERT(dimension == SHADER_2D || mRenderer->isES3Capable());
- ID3D11Device *device = mRenderer->getDevice();
-
switch (blitShaderType)
{
- case BLITSHADER_2D_RGBAF:
- addBlitShaderToMap(blitShaderType, SHADER_2D, d3d11::CompilePS(device, g_PS_PassthroughRGBA2D, "Blit11 2D RGBA pixel shader"));
- break;
- case BLITSHADER_2D_BGRAF:
- addBlitShaderToMap(blitShaderType, SHADER_2D, d3d11::CompilePS(device, g_PS_PassthroughRGBA2D, "Blit11 2D BGRA pixel shader"));
- break;
- case BLITSHADER_2D_RGBF:
- addBlitShaderToMap(blitShaderType, SHADER_2D, d3d11::CompilePS(device, g_PS_PassthroughRGB2D, "Blit11 2D RGB pixel shader"));
- break;
- case BLITSHADER_2D_RGF:
- addBlitShaderToMap(blitShaderType, SHADER_2D, d3d11::CompilePS(device, g_PS_PassthroughRG2D, "Blit11 2D RG pixel shader"));
- break;
- case BLITSHADER_2D_RF:
- addBlitShaderToMap(blitShaderType, SHADER_2D, d3d11::CompilePS(device, g_PS_PassthroughR2D, "Blit11 2D R pixel shader"));
- break;
- case BLITSHADER_2D_ALPHA:
- addBlitShaderToMap(blitShaderType, SHADER_2D, d3d11::CompilePS(device, g_PS_PassthroughRGBA2D, "Blit11 2D alpha pixel shader"));
- break;
- case BLITSHADER_2D_LUMA:
- addBlitShaderToMap(blitShaderType, SHADER_2D, d3d11::CompilePS(device, g_PS_PassthroughLum2D, "Blit11 2D lum pixel shader"));
- break;
- case BLITSHADER_2D_LUMAALPHA:
- addBlitShaderToMap(blitShaderType, SHADER_2D, d3d11::CompilePS(device, g_PS_PassthroughLumAlpha2D, "Blit11 2D luminance alpha pixel shader"));
- break;
- case BLITSHADER_2D_RGBAUI:
- addBlitShaderToMap(blitShaderType, SHADER_2D, d3d11::CompilePS(device, g_PS_PassthroughRGBA2DUI, "Blit11 2D RGBA UI pixel shader"));
- break;
- case BLITSHADER_2D_RGBAI:
- addBlitShaderToMap(blitShaderType, SHADER_2D, d3d11::CompilePS(device, g_PS_PassthroughRGBA2DI, "Blit11 2D RGBA I pixel shader"));
- break;
- case BLITSHADER_2D_RGBUI:
- addBlitShaderToMap(blitShaderType, SHADER_2D, d3d11::CompilePS(device, g_PS_PassthroughRGB2DUI, "Blit11 2D RGB UI pixel shader"));
- break;
- case BLITSHADER_2D_RGBI:
- addBlitShaderToMap(blitShaderType, SHADER_2D, d3d11::CompilePS(device, g_PS_PassthroughRGB2DI, "Blit11 2D RGB I pixel shader"));
- break;
- case BLITSHADER_2D_RGUI:
- addBlitShaderToMap(blitShaderType, SHADER_2D, d3d11::CompilePS(device, g_PS_PassthroughRG2DUI, "Blit11 2D RG UI pixel shader"));
- break;
- case BLITSHADER_2D_RGI:
- addBlitShaderToMap(blitShaderType, SHADER_2D, d3d11::CompilePS(device, g_PS_PassthroughRG2DI, "Blit11 2D RG I pixel shader"));
- break;
- case BLITSHADER_2D_RUI:
- addBlitShaderToMap(blitShaderType, SHADER_2D, d3d11::CompilePS(device, g_PS_PassthroughR2DUI, "Blit11 2D R UI pixel shader"));
- break;
- case BLITSHADER_2D_RI:
- addBlitShaderToMap(blitShaderType, SHADER_2D, d3d11::CompilePS(device, g_PS_PassthroughR2DI, "Blit11 2D R I pixel shader"));
- break;
- case BLITSHADER_3D_RGBAF:
- addBlitShaderToMap(blitShaderType, SHADER_3D, d3d11::CompilePS(device, g_PS_PassthroughRGBA3D, "Blit11 3D RGBA pixel shader"));
- break;
- case BLITSHADER_3D_RGBAUI:
- addBlitShaderToMap(blitShaderType, SHADER_3D, d3d11::CompilePS(device, g_PS_PassthroughRGBA3DUI, "Blit11 3D UI RGBA pixel shader"));
- break;
- case BLITSHADER_3D_RGBAI:
- addBlitShaderToMap(blitShaderType, SHADER_3D, d3d11::CompilePS(device, g_PS_PassthroughRGBA3DI, "Blit11 3D I RGBA pixel shader"));
- break;
- case BLITSHADER_3D_BGRAF:
- addBlitShaderToMap(blitShaderType, SHADER_3D, d3d11::CompilePS(device, g_PS_PassthroughRGBA3D, "Blit11 3D BGRA pixel shader"));
- break;
- case BLITSHADER_3D_RGBF:
- addBlitShaderToMap(blitShaderType, SHADER_3D, d3d11::CompilePS(device, g_PS_PassthroughRGB3D, "Blit11 3D RGB pixel shader"));
- break;
- case BLITSHADER_3D_RGBUI:
- addBlitShaderToMap(blitShaderType, SHADER_3D, d3d11::CompilePS(device, g_PS_PassthroughRGB3DUI, "Blit11 3D RGB UI pixel shader"));
- break;
- case BLITSHADER_3D_RGBI:
- addBlitShaderToMap(blitShaderType, SHADER_3D, d3d11::CompilePS(device, g_PS_PassthroughRGB3DI, "Blit11 3D RGB I pixel shader"));
- break;
- case BLITSHADER_3D_RGF:
- addBlitShaderToMap(blitShaderType, SHADER_3D, d3d11::CompilePS(device, g_PS_PassthroughRG3D, "Blit11 3D RG pixel shader"));
- break;
- case BLITSHADER_3D_RGUI:
- addBlitShaderToMap(blitShaderType, SHADER_3D, d3d11::CompilePS(device, g_PS_PassthroughRG3DUI, "Blit11 3D RG UI pixel shader"));
- break;
- case BLITSHADER_3D_RGI:
- addBlitShaderToMap(blitShaderType, SHADER_3D, d3d11::CompilePS(device, g_PS_PassthroughRG3DI, "Blit11 3D RG I pixel shader"));
- break;
- case BLITSHADER_3D_RF:
- addBlitShaderToMap(blitShaderType, SHADER_3D, d3d11::CompilePS(device, g_PS_PassthroughR3D, "Blit11 3D R pixel shader"));
- break;
- case BLITSHADER_3D_RUI:
- addBlitShaderToMap(blitShaderType, SHADER_3D, d3d11::CompilePS(device, g_PS_PassthroughR3DUI, "Blit11 3D R UI pixel shader"));
- break;
- case BLITSHADER_3D_RI:
- addBlitShaderToMap(blitShaderType, SHADER_3D, d3d11::CompilePS(device, g_PS_PassthroughR3DI, "Blit11 3D R I pixel shader"));
- break;
- case BLITSHADER_3D_ALPHA:
- addBlitShaderToMap(blitShaderType, SHADER_3D, d3d11::CompilePS(device, g_PS_PassthroughRGBA3D, "Blit11 3D alpha pixel shader"));
- break;
- case BLITSHADER_3D_LUMA:
- addBlitShaderToMap(blitShaderType, SHADER_3D, d3d11::CompilePS(device, g_PS_PassthroughLum3D, "Blit11 3D luminance pixel shader"));
- break;
- case BLITSHADER_3D_LUMAALPHA:
- addBlitShaderToMap(blitShaderType, SHADER_3D, d3d11::CompilePS(device, g_PS_PassthroughLumAlpha3D, "Blit11 3D luminance alpha pixel shader"));
- break;
- default:
- UNREACHABLE();
- return gl::Error(GL_INVALID_OPERATION, "Internal error");
+ case BLITSHADER_2D_RGBAF:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D,
+ ShaderData(g_PS_PassthroughRGBA2D),
+ "Blit11 2D RGBA pixel shader"));
+ break;
+ case BLITSHADER_2D_BGRAF:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D,
+ ShaderData(g_PS_PassthroughRGBA2D),
+ "Blit11 2D BGRA pixel shader"));
+ break;
+ case BLITSHADER_2D_RGBF:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D,
+ ShaderData(g_PS_PassthroughRGB2D),
+ "Blit11 2D RGB pixel shader"));
+ break;
+ case BLITSHADER_2D_RGF:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D,
+ ShaderData(g_PS_PassthroughRG2D),
+ "Blit11 2D RG pixel shader"));
+ break;
+ case BLITSHADER_2D_RF:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D, ShaderData(g_PS_PassthroughR2D),
+ "Blit11 2D R pixel shader"));
+ break;
+ case BLITSHADER_2D_ALPHA:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D, ShaderData(g_PS_PassthroughA2D),
+ "Blit11 2D alpha pixel shader"));
+ break;
+ case BLITSHADER_2D_LUMA:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D,
+ ShaderData(g_PS_PassthroughLum2D),
+ "Blit11 2D lum pixel shader"));
+ break;
+ case BLITSHADER_2D_LUMAALPHA:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D,
+ ShaderData(g_PS_PassthroughLumAlpha2D),
+ "Blit11 2D luminance alpha pixel shader"));
+ break;
+ case BLITSHADER_2D_RGBAUI:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D,
+ ShaderData(g_PS_PassthroughRGBA2DUI),
+ "Blit11 2D RGBA UI pixel shader"));
+ break;
+ case BLITSHADER_2D_RGBAI:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D,
+ ShaderData(g_PS_PassthroughRGBA2DI),
+ "Blit11 2D RGBA I pixel shader"));
+ break;
+ case BLITSHADER_2D_RGBUI:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D,
+ ShaderData(g_PS_PassthroughRGB2DUI),
+ "Blit11 2D RGB UI pixel shader"));
+ break;
+ case BLITSHADER_2D_RGBI:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D,
+ ShaderData(g_PS_PassthroughRGB2DI),
+ "Blit11 2D RGB I pixel shader"));
+ break;
+ case BLITSHADER_2D_RGUI:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D,
+ ShaderData(g_PS_PassthroughRG2DUI),
+ "Blit11 2D RG UI pixel shader"));
+ break;
+ case BLITSHADER_2D_RGI:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D,
+ ShaderData(g_PS_PassthroughRG2DI),
+ "Blit11 2D RG I pixel shader"));
+ break;
+ case BLITSHADER_2D_RUI:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D,
+ ShaderData(g_PS_PassthroughR2DUI),
+ "Blit11 2D R UI pixel shader"));
+ break;
+ case BLITSHADER_2D_RI:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D,
+ ShaderData(g_PS_PassthroughR2DI),
+ "Blit11 2D R I pixel shader"));
+ break;
+ case BLITSHADER_3D_RGBAF:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_3D,
+ ShaderData(g_PS_PassthroughRGBA3D),
+ "Blit11 3D RGBA pixel shader"));
+ break;
+ case BLITSHADER_3D_RGBAUI:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_3D,
+ ShaderData(g_PS_PassthroughRGBA3DUI),
+ "Blit11 3D UI RGBA pixel shader"));
+ break;
+ case BLITSHADER_3D_RGBAI:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_3D,
+ ShaderData(g_PS_PassthroughRGBA3DI),
+ "Blit11 3D I RGBA pixel shader"));
+ break;
+ case BLITSHADER_3D_BGRAF:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_3D,
+ ShaderData(g_PS_PassthroughRGBA3D),
+ "Blit11 3D BGRA pixel shader"));
+ break;
+ case BLITSHADER_3D_RGBF:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_3D,
+ ShaderData(g_PS_PassthroughRGB3D),
+ "Blit11 3D RGB pixel shader"));
+ break;
+ case BLITSHADER_3D_RGBUI:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_3D,
+ ShaderData(g_PS_PassthroughRGB3DUI),
+ "Blit11 3D RGB UI pixel shader"));
+ break;
+ case BLITSHADER_3D_RGBI:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_3D,
+ ShaderData(g_PS_PassthroughRGB3DI),
+ "Blit11 3D RGB I pixel shader"));
+ break;
+ case BLITSHADER_3D_RGF:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_3D,
+ ShaderData(g_PS_PassthroughRG3D),
+ "Blit11 3D RG pixel shader"));
+ break;
+ case BLITSHADER_3D_RGUI:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_3D,
+ ShaderData(g_PS_PassthroughRG3DUI),
+ "Blit11 3D RG UI pixel shader"));
+ break;
+ case BLITSHADER_3D_RGI:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_3D,
+ ShaderData(g_PS_PassthroughRG3DI),
+ "Blit11 3D RG I pixel shader"));
+ break;
+ case BLITSHADER_3D_RF:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_3D, ShaderData(g_PS_PassthroughR3D),
+ "Blit11 3D R pixel shader"));
+ break;
+ case BLITSHADER_3D_RUI:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_3D,
+ ShaderData(g_PS_PassthroughR3DUI),
+ "Blit11 3D R UI pixel shader"));
+ break;
+ case BLITSHADER_3D_RI:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_3D,
+ ShaderData(g_PS_PassthroughR3DI),
+ "Blit11 3D R I pixel shader"));
+ break;
+ case BLITSHADER_3D_ALPHA:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_3D,
+ ShaderData(g_PS_PassthroughRGBA3D),
+ "Blit11 3D alpha pixel shader"));
+ break;
+ case BLITSHADER_3D_LUMA:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_3D,
+ ShaderData(g_PS_PassthroughLum3D),
+ "Blit11 3D luminance pixel shader"));
+ break;
+ case BLITSHADER_3D_LUMAALPHA:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_3D,
+ ShaderData(g_PS_PassthroughLumAlpha3D),
+ "Blit11 3D luminance alpha pixel shader"));
+ break;
+
+ case BLITSHADER_2D_RGBAF_PREMULTIPLY:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D, ShaderData(g_PS_FtoF_PM_RGBA),
+ "Blit11 2D RGBA premultiply pixel shader"));
+ break;
+
+ case BLITSHADER_2D_RGBAF_UNMULTIPLY:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D, ShaderData(g_PS_FtoF_UM_RGBA),
+ "Blit11 2D RGBA unmultiply pixel shader"));
+ break;
+
+ case BLITSHADER_2D_RGBF_PREMULTIPLY:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D, ShaderData(g_PS_FtoF_PM_RGB),
+ "Blit11 2D RGB premultiply pixel shader"));
+ break;
+
+ case BLITSHADER_2D_RGBF_UNMULTIPLY:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D, ShaderData(g_PS_FtoF_UM_RGB),
+ "Blit11 2D RGB unmultiply pixel shader"));
+ break;
+
+ case BLITSHADER_2D_RGBAF_TOUI:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D, ShaderData(g_PS_FtoU_PT_RGBA),
+ "Blit11 2D RGBA to uint pixel shader"));
+ break;
+
+ case BLITSHADER_2D_RGBAF_TOUI_PREMULTIPLY:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D, ShaderData(g_PS_FtoU_PM_RGBA),
+ "Blit11 2D RGBA to uint premultiply pixel shader"));
+ break;
+
+ case BLITSHADER_2D_RGBAF_TOUI_UNMULTIPLY:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D, ShaderData(g_PS_FtoU_UM_RGBA),
+ "Blit11 2D RGBA to uint unmultiply pixel shader"));
+ break;
+
+ case BLITSHADER_2D_RGBF_TOUI:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D, ShaderData(g_PS_FtoU_PT_RGB),
+ "Blit11 2D RGB to uint pixel shader"));
+ break;
+
+ case BLITSHADER_2D_RGBF_TOUI_PREMULTIPLY:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D, ShaderData(g_PS_FtoU_PM_RGB),
+ "Blit11 2D RGB to uint premultiply pixel shader"));
+ break;
+
+ case BLITSHADER_2D_RGBF_TOUI_UNMULTIPLY:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D, ShaderData(g_PS_FtoU_UM_RGB),
+ "Blit11 2D RGB to uint unmultiply pixel shader"));
+ break;
+ case BLITSHADER_2D_LUMAF_PREMULTIPLY:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D, ShaderData(g_PS_FtoF_PM_LUMA),
+ "Blit11 2D LUMA premultiply pixel shader"));
+ break;
+ case BLITSHADER_2D_LUMAF_UNMULTIPLY:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D, ShaderData(g_PS_FtoF_UM_LUMA),
+ "Blit11 2D LUMA unmultiply pixel shader"));
+ break;
+ case BLITSHADER_2D_LUMAALPHAF_PREMULTIPLY:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D,
+ ShaderData(g_PS_FtoF_PM_LUMAALPHA),
+ "Blit11 2D LUMAALPHA premultiply pixel shader"));
+ break;
+ case BLITSHADER_2D_LUMAALPHAF_UNMULTIPLY:
+ ANGLE_TRY(addBlitShaderToMap(blitShaderType, SHADER_2D,
+ ShaderData(g_PS_FtoF_UM_LUMAALPHA),
+ "Blit11 2D LUMAALPHA unmultiply pixel shader"));
+ break;
+
+ default:
+ UNREACHABLE();
+ return gl::InternalError() << "Internal error";
}
blitShaderIt = mBlitShaderMap.find(blitShaderType);
ASSERT(blitShaderIt != mBlitShaderMap.end());
*shader = &blitShaderIt->second;
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error Blit11::getSwizzleShader(GLenum type, D3D11_SRV_DIMENSION viewDimension, const Shader **shader)
+gl::Error Blit11::getSwizzleShader(GLenum type,
+ D3D11_SRV_DIMENSION viewDimension,
+ const Shader **shader)
{
SwizzleShaderType swizzleShaderType = GetSwizzleShaderType(type, viewDimension);
if (swizzleShaderType == SWIZZLESHADER_INVALID)
{
- return gl::Error(GL_INVALID_OPERATION, "Swizzle shader type not found");
+ return gl::InternalError() << "Swizzle shader type not found";
}
auto swizzleShaderIt = mSwizzleShaderMap.find(swizzleShaderType);
if (swizzleShaderIt != mSwizzleShaderMap.end())
{
*shader = &swizzleShaderIt->second;
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
// Swizzling shaders (OpenGL ES 3+)
ASSERT(mRenderer->isES3Capable());
- ID3D11Device *device = mRenderer->getDevice();
-
switch (swizzleShaderType)
{
- case SWIZZLESHADER_2D_FLOAT:
- addSwizzleShaderToMap(swizzleShaderType, SHADER_2D, d3d11::CompilePS(device, g_PS_SwizzleF2D, "Blit11 2D F swizzle pixel shader"));
- break;
- case SWIZZLESHADER_2D_UINT:
- addSwizzleShaderToMap(swizzleShaderType, SHADER_2D, d3d11::CompilePS(device, g_PS_SwizzleUI2D, "Blit11 2D UI swizzle pixel shader"));
- break;
- case SWIZZLESHADER_2D_INT:
- addSwizzleShaderToMap(swizzleShaderType, SHADER_2D, d3d11::CompilePS(device, g_PS_SwizzleI2D, "Blit11 2D I swizzle pixel shader"));
- break;
- case SWIZZLESHADER_CUBE_FLOAT:
- addSwizzleShaderToMap(swizzleShaderType, SHADER_3D, d3d11::CompilePS(device, g_PS_SwizzleF2DArray, "Blit11 2D Cube F swizzle pixel shader"));
- break;
- case SWIZZLESHADER_CUBE_UINT:
- addSwizzleShaderToMap(swizzleShaderType, SHADER_3D, d3d11::CompilePS(device, g_PS_SwizzleUI2DArray, "Blit11 2D Cube UI swizzle pixel shader"));
- break;
- case SWIZZLESHADER_CUBE_INT:
- addSwizzleShaderToMap(swizzleShaderType, SHADER_3D, d3d11::CompilePS(device, g_PS_SwizzleI2DArray, "Blit11 2D Cube I swizzle pixel shader"));
- break;
- case SWIZZLESHADER_3D_FLOAT:
- addSwizzleShaderToMap(swizzleShaderType, SHADER_3D, d3d11::CompilePS(device, g_PS_SwizzleF3D, "Blit11 3D F swizzle pixel shader"));
- break;
- case SWIZZLESHADER_3D_UINT:
- addSwizzleShaderToMap(swizzleShaderType, SHADER_3D, d3d11::CompilePS(device, g_PS_SwizzleUI3D, "Blit11 3D UI swizzle pixel shader"));
- break;
- case SWIZZLESHADER_3D_INT:
- addSwizzleShaderToMap(swizzleShaderType, SHADER_3D, d3d11::CompilePS(device, g_PS_SwizzleI3D, "Blit11 3D I swizzle pixel shader"));
- break;
- case SWIZZLESHADER_ARRAY_FLOAT:
- addSwizzleShaderToMap(swizzleShaderType, SHADER_3D, d3d11::CompilePS(device, g_PS_SwizzleF2DArray, "Blit11 2D Array F swizzle pixel shader"));
- break;
- case SWIZZLESHADER_ARRAY_UINT:
- addSwizzleShaderToMap(swizzleShaderType, SHADER_3D, d3d11::CompilePS(device, g_PS_SwizzleUI2DArray, "Blit11 2D Array UI swizzle pixel shader"));
- break;
- case SWIZZLESHADER_ARRAY_INT:
- addSwizzleShaderToMap(swizzleShaderType, SHADER_3D, d3d11::CompilePS(device, g_PS_SwizzleI2DArray, "Blit11 2D Array I swizzle pixel shader"));
- break;
- default:
- UNREACHABLE();
- return gl::Error(GL_INVALID_OPERATION, "Internal error");
+ case SWIZZLESHADER_2D_FLOAT:
+ ANGLE_TRY(addSwizzleShaderToMap(swizzleShaderType, SHADER_2D,
+ ShaderData(g_PS_SwizzleF2D),
+ "Blit11 2D F swizzle pixel shader"));
+ break;
+ case SWIZZLESHADER_2D_UINT:
+ ANGLE_TRY(addSwizzleShaderToMap(swizzleShaderType, SHADER_2D,
+ ShaderData(g_PS_SwizzleUI2D),
+ "Blit11 2D UI swizzle pixel shader"));
+ break;
+ case SWIZZLESHADER_2D_INT:
+ ANGLE_TRY(addSwizzleShaderToMap(swizzleShaderType, SHADER_2D,
+ ShaderData(g_PS_SwizzleI2D),
+ "Blit11 2D I swizzle pixel shader"));
+ break;
+ case SWIZZLESHADER_CUBE_FLOAT:
+ ANGLE_TRY(addSwizzleShaderToMap(swizzleShaderType, SHADER_3D,
+ ShaderData(g_PS_SwizzleF2DArray),
+ "Blit11 2D Cube F swizzle pixel shader"));
+ break;
+ case SWIZZLESHADER_CUBE_UINT:
+ ANGLE_TRY(addSwizzleShaderToMap(swizzleShaderType, SHADER_3D,
+ ShaderData(g_PS_SwizzleUI2DArray),
+ "Blit11 2D Cube UI swizzle pixel shader"));
+ break;
+ case SWIZZLESHADER_CUBE_INT:
+ ANGLE_TRY(addSwizzleShaderToMap(swizzleShaderType, SHADER_3D,
+ ShaderData(g_PS_SwizzleI2DArray),
+ "Blit11 2D Cube I swizzle pixel shader"));
+ break;
+ case SWIZZLESHADER_3D_FLOAT:
+ ANGLE_TRY(addSwizzleShaderToMap(swizzleShaderType, SHADER_3D,
+ ShaderData(g_PS_SwizzleF3D),
+ "Blit11 3D F swizzle pixel shader"));
+ break;
+ case SWIZZLESHADER_3D_UINT:
+ ANGLE_TRY(addSwizzleShaderToMap(swizzleShaderType, SHADER_3D,
+ ShaderData(g_PS_SwizzleUI3D),
+ "Blit11 3D UI swizzle pixel shader"));
+ break;
+ case SWIZZLESHADER_3D_INT:
+ ANGLE_TRY(addSwizzleShaderToMap(swizzleShaderType, SHADER_3D,
+ ShaderData(g_PS_SwizzleI3D),
+ "Blit11 3D I swizzle pixel shader"));
+ break;
+ case SWIZZLESHADER_ARRAY_FLOAT:
+ ANGLE_TRY(addSwizzleShaderToMap(swizzleShaderType, SHADER_3D,
+ ShaderData(g_PS_SwizzleF2DArray),
+ "Blit11 2D Array F swizzle pixel shader"));
+ break;
+ case SWIZZLESHADER_ARRAY_UINT:
+ ANGLE_TRY(addSwizzleShaderToMap(swizzleShaderType, SHADER_3D,
+ ShaderData(g_PS_SwizzleUI2DArray),
+ "Blit11 2D Array UI swizzle pixel shader"));
+ break;
+ case SWIZZLESHADER_ARRAY_INT:
+ ANGLE_TRY(addSwizzleShaderToMap(swizzleShaderType, SHADER_3D,
+ ShaderData(g_PS_SwizzleI2DArray),
+ "Blit11 2D Array I swizzle pixel shader"));
+ break;
+ default:
+ UNREACHABLE();
+ return gl::InternalError() << "Internal error";
}
swizzleShaderIt = mSwizzleShaderMap.find(swizzleShaderType);
ASSERT(swizzleShaderIt != mSwizzleShaderMap.end());
*shader = &swizzleShaderIt->second;
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
+gl::ErrorOrResult<TextureHelper11> Blit11::resolveDepth(const gl::Context *context,
+ RenderTarget11 *depth)
+{
+ ANGLE_TRY(initResources());
+
+ // Multisampled depth stencil SRVs are not available in feature level 10.0
+ ASSERT(mRenderer->getRenderer11DeviceCaps().featureLevel > D3D_FEATURE_LEVEL_10_0);
+
+ const auto &extents = depth->getExtents();
+ auto *deviceContext = mRenderer->getDeviceContext();
+ auto *stateManager = mRenderer->getStateManager();
+
+ ANGLE_TRY(initResolveDepthOnly(depth->getFormatSet(), extents));
+
+ ANGLE_TRY(mResolveDepthStencilVS.resolve(mRenderer));
+ ANGLE_TRY(mResolveDepthPS.resolve(mRenderer));
+
+ // Apply the necessary state changes to the D3D11 immediate device context.
+ stateManager->setInputLayout(nullptr);
+ stateManager->setPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST);
+ stateManager->setDrawShaders(&mResolveDepthStencilVS.getObj(), nullptr,
+ &mResolveDepthPS.getObj());
+ stateManager->setRasterizerState(nullptr);
+ stateManager->setDepthStencilState(&mDepthStencilState, 0xFFFFFFFF);
+ stateManager->setRenderTargets(nullptr, 0, mResolvedDepthDSView.get());
+ stateManager->setSimpleBlendState(nullptr);
+ stateManager->setSimpleViewport(extents);
+
+ // Set the viewport
+ stateManager->setShaderResourceShared(gl::SAMPLER_PIXEL, 0, &depth->getShaderResourceView());
+
+ // Trigger the blit on the GPU.
+ deviceContext->Draw(6, 0);
+
+ return mResolvedDepth;
}
+
+gl::Error Blit11::initResolveDepthOnly(const d3d11::Format &format, const gl::Extents &extents)
+{
+ if (mResolvedDepth.valid() && extents == mResolvedDepth.getExtents() &&
+ format.texFormat == mResolvedDepth.getFormat())
+ {
+ return gl::NoError();
+ }
+
+ D3D11_TEXTURE2D_DESC textureDesc;
+ textureDesc.Width = extents.width;
+ textureDesc.Height = extents.height;
+ textureDesc.MipLevels = 1;
+ textureDesc.ArraySize = 1;
+ textureDesc.Format = format.texFormat;
+ textureDesc.SampleDesc.Count = 1;
+ textureDesc.SampleDesc.Quality = 0;
+ textureDesc.Usage = D3D11_USAGE_DEFAULT;
+ textureDesc.BindFlags = D3D11_BIND_DEPTH_STENCIL | D3D11_BIND_SHADER_RESOURCE;
+ textureDesc.CPUAccessFlags = 0;
+ textureDesc.MiscFlags = 0;
+
+ ANGLE_TRY(mRenderer->allocateTexture(textureDesc, format, &mResolvedDepth));
+ mResolvedDepth.setDebugName("Blit11::mResolvedDepth");
+
+ D3D11_DEPTH_STENCIL_VIEW_DESC dsvDesc;
+ dsvDesc.Flags = 0;
+ dsvDesc.Format = format.dsvFormat;
+ dsvDesc.Texture2D.MipSlice = 0;
+ dsvDesc.ViewDimension = D3D11_DSV_DIMENSION_TEXTURE2D;
+
+ ANGLE_TRY(mRenderer->allocateResource(dsvDesc, mResolvedDepth.get(), &mResolvedDepthDSView));
+ mResolvedDepthDSView.setDebugName("Blit11::mResolvedDepthDSView");
+
+ // Possibly D3D11 bug or undefined behaviour: Clear the DSV so that our first render
+ // works as expected. Otherwise the results of the first use seem to be incorrect.
+ ID3D11DeviceContext *context = mRenderer->getDeviceContext();
+ context->ClearDepthStencilView(mResolvedDepthDSView.get(), D3D11_CLEAR_DEPTH, 1.0f, 0);
+
+ return gl::NoError();
+}
+
+gl::Error Blit11::initResolveDepthStencil(const gl::Extents &extents)
+{
+ // Check if we need to recreate depth stencil view
+ if (mResolvedDepthStencil.valid() && extents == mResolvedDepthStencil.getExtents())
+ {
+ ASSERT(mResolvedDepthStencil.getFormat() == DXGI_FORMAT_R32G32_FLOAT);
+ return gl::NoError();
+ }
+
+ if (mResolvedDepthStencil.valid())
+ {
+ releaseResolveDepthStencilResources();
+ }
+
+ const auto &formatSet = d3d11::Format::Get(GL_RG32F, mRenderer->getRenderer11DeviceCaps());
+
+ D3D11_TEXTURE2D_DESC textureDesc;
+ textureDesc.Width = extents.width;
+ textureDesc.Height = extents.height;
+ textureDesc.MipLevels = 1;
+ textureDesc.ArraySize = 1;
+ textureDesc.Format = formatSet.texFormat;
+ textureDesc.SampleDesc.Count = 1;
+ textureDesc.SampleDesc.Quality = 0;
+ textureDesc.Usage = D3D11_USAGE_DEFAULT;
+ textureDesc.BindFlags = D3D11_BIND_RENDER_TARGET;
+ textureDesc.CPUAccessFlags = 0;
+ textureDesc.MiscFlags = 0;
+
+ ANGLE_TRY(mRenderer->allocateTexture(textureDesc, formatSet, &mResolvedDepthStencil));
+ mResolvedDepthStencil.setDebugName("Blit11::mResolvedDepthStencil");
+
+ ANGLE_TRY(mRenderer->allocateResourceNoDesc(mResolvedDepthStencil.get(),
+ &mResolvedDepthStencilRTView));
+ mResolvedDepthStencilRTView.setDebugName("Blit11::mResolvedDepthStencilRTView");
+
+ return gl::NoError();
+}
+
+gl::ErrorOrResult<TextureHelper11> Blit11::resolveStencil(const gl::Context *context,
+ RenderTarget11 *depthStencil,
+ bool alsoDepth)
+{
+ ANGLE_TRY(initResources());
+
+ // Multisampled depth stencil SRVs are not available in feature level 10.0
+ ASSERT(mRenderer->getRenderer11DeviceCaps().featureLevel > D3D_FEATURE_LEVEL_10_0);
+
+ const auto &extents = depthStencil->getExtents();
+
+ ANGLE_TRY(initResolveDepthStencil(extents));
+
+ ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
+ auto *stateManager = mRenderer->getStateManager();
+ ID3D11Resource *stencilResource = depthStencil->getTexture().get();
+
+ // Check if we need to re-create the stencil SRV.
+ if (mStencilSRV.valid())
+ {
+ ID3D11Resource *priorResource = nullptr;
+ mStencilSRV.get()->GetResource(&priorResource);
+
+ if (stencilResource != priorResource)
+ {
+ mStencilSRV.reset();
+ }
+
+ SafeRelease(priorResource);
+ }
+
+ if (!mStencilSRV.valid())
+ {
+ D3D11_SHADER_RESOURCE_VIEW_DESC srViewDesc;
+ srViewDesc.Format = GetStencilSRVFormat(depthStencil->getFormatSet());
+ srViewDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2DMS;
+
+ ANGLE_TRY(mRenderer->allocateResource(srViewDesc, stencilResource, &mStencilSRV));
+ mStencilSRV.setDebugName("Blit11::mStencilSRV");
+ }
+
+ // Notify the Renderer that all state should be invalidated.
+ ANGLE_TRY(mResolveDepthStencilVS.resolve(mRenderer));
+
+ // Resolving the depth buffer works by sampling the depth in the shader using a SRV, then
+ // writing to the resolved depth buffer using SV_Depth. We can't use this method for stencil
+ // because SV_StencilRef isn't supported until HLSL 5.1/D3D11.3.
+ const d3d11::PixelShader *pixelShader = nullptr;
+ if (alsoDepth)
+ {
+ ANGLE_TRY(mResolveDepthStencilPS.resolve(mRenderer));
+ pixelShader = &mResolveDepthStencilPS.getObj();
+ }
+ else
+ {
+ ANGLE_TRY(mResolveStencilPS.resolve(mRenderer));
+ pixelShader = &mResolveStencilPS.getObj();
+ }
+
+ // Apply the necessary state changes to the D3D11 immediate device context.
+ stateManager->setInputLayout(nullptr);
+ stateManager->setPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST);
+ stateManager->setDrawShaders(&mResolveDepthStencilVS.getObj(), nullptr, pixelShader);
+ stateManager->setRasterizerState(nullptr);
+ stateManager->setDepthStencilState(nullptr, 0xFFFFFFFF);
+ stateManager->setRenderTarget(mResolvedDepthStencilRTView.get(), nullptr);
+ stateManager->setSimpleBlendState(nullptr);
+
+ // Set the viewport
+ stateManager->setSimpleViewport(extents);
+ stateManager->setShaderResourceShared(gl::SAMPLER_PIXEL, 0,
+ &depthStencil->getShaderResourceView());
+ stateManager->setShaderResource(gl::SAMPLER_PIXEL, 1, &mStencilSRV);
+
+ // Trigger the blit on the GPU.
+ deviceContext->Draw(6, 0);
+
+ gl::Box copyBox(0, 0, 0, extents.width, extents.height, 1);
+
+ TextureHelper11 dest;
+ ANGLE_TRY_RESULT(
+ mRenderer->createStagingTexture(ResourceType::Texture2D, depthStencil->getFormatSet(),
+ extents, StagingAccess::READ_WRITE),
+ dest);
+
+ const auto &copyFunction = GetCopyDepthStencilFunction(depthStencil->getInternalFormat());
+ const auto &dsFormatSet = depthStencil->getFormatSet();
+ const auto &dsDxgiInfo = d3d11::GetDXGIFormatSizeInfo(dsFormatSet.texFormat);
+
+ ANGLE_TRY(copyAndConvertImpl(mResolvedDepthStencil, 0, copyBox, extents, dest, copyBox, extents,
+ nullptr, 0, 0, 0, 8u, dsDxgiInfo.pixelBytes, copyFunction));
+
+ // Return the resolved depth texture, which the caller must Release.
+ return dest;
+}
+
+void Blit11::releaseResolveDepthStencilResources()
+{
+ mStencilSRV.reset();
+ mResolvedDepthStencilRTView.reset();
+}
+
+} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Blit11.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Blit11.h
index 906616131e..14078f9db8 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Blit11.h
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Blit11.h
@@ -10,8 +10,9 @@
#define LIBANGLE_RENDERER_D3D_D3D11_BLIT11_H_
#include "common/angleutils.h"
-#include "libANGLE/angletypes.h"
#include "libANGLE/Error.h"
+#include "libANGLE/angletypes.h"
+#include "libANGLE/renderer/d3d/d3d11/ResourceManager11.h"
#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
#include <map>
@@ -26,36 +27,84 @@ class Blit11 : angle::NonCopyable
explicit Blit11(Renderer11 *renderer);
~Blit11();
- gl::Error swizzleTexture(ID3D11ShaderResourceView *source, ID3D11RenderTargetView *dest, const gl::Extents &size,
- GLenum swizzleRed, GLenum swizzleGreen, GLenum swizzleBlue, GLenum swizzleAlpha);
+ gl::Error swizzleTexture(const gl::Context *context,
+ const d3d11::SharedSRV &source,
+ const d3d11::RenderTargetView &dest,
+ const gl::Extents &size,
+ const gl::SwizzleState &swizzleTarget);
- gl::Error copyTexture(ID3D11ShaderResourceView *source,
+ gl::Error copyTexture(const gl::Context *context,
+ const d3d11::SharedSRV &source,
const gl::Box &sourceArea,
const gl::Extents &sourceSize,
- ID3D11RenderTargetView *dest,
+ GLenum sourceFormat,
+ const d3d11::RenderTargetView &dest,
const gl::Box &destArea,
const gl::Extents &destSize,
const gl::Rectangle *scissor,
GLenum destFormat,
GLenum filter,
- bool maskOffAlpha);
+ bool maskOffAlpha,
+ bool unpackPremultiplyAlpha,
+ bool unpackUnmultiplyAlpha);
- gl::Error copyStencil(ID3D11Resource *source, unsigned int sourceSubresource, const gl::Box &sourceArea, const gl::Extents &sourceSize,
- ID3D11Resource *dest, unsigned int destSubresource, const gl::Box &destArea, const gl::Extents &destSize,
+ gl::Error copyStencil(const gl::Context *context,
+ const TextureHelper11 &source,
+ unsigned int sourceSubresource,
+ const gl::Box &sourceArea,
+ const gl::Extents &sourceSize,
+ const TextureHelper11 &dest,
+ unsigned int destSubresource,
+ const gl::Box &destArea,
+ const gl::Extents &destSize,
const gl::Rectangle *scissor);
- gl::Error copyDepth(ID3D11ShaderResourceView *source, const gl::Box &sourceArea, const gl::Extents &sourceSize,
- ID3D11DepthStencilView *dest, const gl::Box &destArea, const gl::Extents &destSize,
+ gl::Error copyDepth(const gl::Context *context,
+ const d3d11::SharedSRV &source,
+ const gl::Box &sourceArea,
+ const gl::Extents &sourceSize,
+ const d3d11::DepthStencilView &dest,
+ const gl::Box &destArea,
+ const gl::Extents &destSize,
const gl::Rectangle *scissor);
- gl::Error copyDepthStencil(ID3D11Resource *source, unsigned int sourceSubresource, const gl::Box &sourceArea, const gl::Extents &sourceSize,
- ID3D11Resource *dest, unsigned int destSubresource, const gl::Box &destArea, const gl::Extents &destSize,
+ gl::Error copyDepthStencil(const TextureHelper11 &source,
+ unsigned int sourceSubresource,
+ const gl::Box &sourceArea,
+ const gl::Extents &sourceSize,
+ const TextureHelper11 &dest,
+ unsigned int destSubresource,
+ const gl::Box &destArea,
+ const gl::Extents &destSize,
const gl::Rectangle *scissor);
+ gl::ErrorOrResult<TextureHelper11> resolveDepth(const gl::Context *context,
+ RenderTarget11 *depth);
+
+ gl::ErrorOrResult<TextureHelper11> resolveStencil(const gl::Context *context,
+ RenderTarget11 *depthStencil,
+ bool alsoDepth);
+
+ using BlitConvertFunction = void(const gl::Box &sourceArea,
+ const gl::Box &destArea,
+ const gl::Rectangle &clipRect,
+ const gl::Extents &sourceSize,
+ unsigned int sourceRowPitch,
+ unsigned int destRowPitch,
+ ptrdiff_t readOffset,
+ ptrdiff_t writeOffset,
+ size_t copySize,
+ size_t srcPixelStride,
+ size_t destPixelStride,
+ const uint8_t *sourceData,
+ uint8_t *destData);
+
private:
enum BlitShaderType
{
BLITSHADER_INVALID,
+
+ // Passthrough shaders
BLITSHADER_2D_RGBAF,
BLITSHADER_2D_BGRAF,
BLITSHADER_2D_RGBF,
@@ -88,6 +137,27 @@ class Blit11 : angle::NonCopyable
BLITSHADER_3D_ALPHA,
BLITSHADER_3D_LUMA,
BLITSHADER_3D_LUMAALPHA,
+
+ // Multiply alpha shaders
+ BLITSHADER_2D_RGBAF_PREMULTIPLY,
+ BLITSHADER_2D_RGBAF_UNMULTIPLY,
+
+ BLITSHADER_2D_RGBF_PREMULTIPLY,
+ BLITSHADER_2D_RGBF_UNMULTIPLY,
+
+ BLITSHADER_2D_RGBAF_TOUI,
+ BLITSHADER_2D_RGBAF_TOUI_PREMULTIPLY,
+ BLITSHADER_2D_RGBAF_TOUI_UNMULTIPLY,
+
+ BLITSHADER_2D_RGBF_TOUI,
+ BLITSHADER_2D_RGBF_TOUI_PREMULTIPLY,
+ BLITSHADER_2D_RGBF_TOUI_UNMULTIPLY,
+
+ BLITSHADER_2D_LUMAF_PREMULTIPLY,
+ BLITSHADER_2D_LUMAF_UNMULTIPLY,
+
+ BLITSHADER_2D_LUMAALPHAF_PREMULTIPLY,
+ BLITSHADER_2D_LUMAALPHAF_UNMULTIPLY
};
enum SwizzleShaderType
@@ -107,9 +177,13 @@ class Blit11 : angle::NonCopyable
SWIZZLESHADER_ARRAY_INT,
};
- typedef void (*WriteVertexFunction)(const gl::Box &sourceArea, const gl::Extents &sourceSize,
- const gl::Box &destArea, const gl::Extents &destSize,
- void *outVertices, unsigned int *outStride, unsigned int *outVertexCount,
+ typedef void (*WriteVertexFunction)(const gl::Box &sourceArea,
+ const gl::Extents &sourceSize,
+ const gl::Box &destArea,
+ const gl::Extents &destSize,
+ void *outVertices,
+ unsigned int *outStride,
+ unsigned int *outVertexCount,
D3D11_PRIMITIVE_TOPOLOGY *outTopology);
enum ShaderDimension
@@ -120,38 +194,102 @@ class Blit11 : angle::NonCopyable
struct Shader
{
+ Shader();
+ Shader(Shader &&other);
+ ~Shader();
+ Shader &operator=(Shader &&other);
+
ShaderDimension dimension;
- ID3D11PixelShader *pixelShader;
+ d3d11::PixelShader pixelShader;
};
struct ShaderSupport
{
- ID3D11InputLayout *inputLayout;
- ID3D11VertexShader *vertexShader;
- ID3D11GeometryShader *geometryShader;
+ const d3d11::InputLayout *inputLayout;
+ const d3d11::VertexShader *vertexShader;
+ const d3d11::GeometryShader *geometryShader;
WriteVertexFunction vertexWriteFunction;
};
gl::Error initResources();
- void freeResources();
- ShaderSupport getShaderSupport(const Shader &shader);
+ gl::Error getShaderSupport(const Shader &shader, ShaderSupport *supportOut);
- static BlitShaderType GetBlitShaderType(GLenum destinationFormat, bool isSigned, ShaderDimension dimension);
+ static BlitShaderType GetBlitShaderType(GLenum destinationFormat,
+ GLenum sourceFormat,
+ bool isSigned,
+ bool unpackPremultiplyAlpha,
+ bool unpackUnmultiplyAlpha,
+ ShaderDimension dimension);
static SwizzleShaderType GetSwizzleShaderType(GLenum type, D3D11_SRV_DIMENSION dimensionality);
- gl::Error copyDepthStencil(ID3D11Resource *source, unsigned int sourceSubresource, const gl::Box &sourceArea, const gl::Extents &sourceSize,
- ID3D11Resource *dest, unsigned int destSubresource, const gl::Box &destArea, const gl::Extents &destSize,
- const gl::Rectangle *scissor, bool stencilOnly);
-
- void addBlitShaderToMap(BlitShaderType blitShaderType, ShaderDimension dimension, ID3D11PixelShader *ps);
-
- gl::Error getBlitShader(GLenum destFormat, bool isSigned, ShaderDimension dimension, const Shader **shaderOut);
- gl::Error getSwizzleShader(GLenum type, D3D11_SRV_DIMENSION viewDimension, const Shader **shaderOut);
-
- void addSwizzleShaderToMap(SwizzleShaderType swizzleShaderType, ShaderDimension dimension, ID3D11PixelShader *ps);
+ gl::Error copyDepthStencilImpl(const TextureHelper11 &source,
+ unsigned int sourceSubresource,
+ const gl::Box &sourceArea,
+ const gl::Extents &sourceSize,
+ const TextureHelper11 &dest,
+ unsigned int destSubresource,
+ const gl::Box &destArea,
+ const gl::Extents &destSize,
+ const gl::Rectangle *scissor,
+ bool stencilOnly);
+
+ gl::Error copyAndConvertImpl(const TextureHelper11 &source,
+ unsigned int sourceSubresource,
+ const gl::Box &sourceArea,
+ const gl::Extents &sourceSize,
+ const TextureHelper11 &destStaging,
+ const gl::Box &destArea,
+ const gl::Extents &destSize,
+ const gl::Rectangle *scissor,
+ size_t readOffset,
+ size_t writeOffset,
+ size_t copySize,
+ size_t srcPixelStride,
+ size_t destPixelStride,
+ BlitConvertFunction *convertFunction);
+
+ gl::Error copyAndConvert(const TextureHelper11 &source,
+ unsigned int sourceSubresource,
+ const gl::Box &sourceArea,
+ const gl::Extents &sourceSize,
+ const TextureHelper11 &dest,
+ unsigned int destSubresource,
+ const gl::Box &destArea,
+ const gl::Extents &destSize,
+ const gl::Rectangle *scissor,
+ size_t readOffset,
+ size_t writeOffset,
+ size_t copySize,
+ size_t srcPixelStride,
+ size_t destPixelStride,
+ BlitConvertFunction *convertFunction);
+
+ gl::Error addBlitShaderToMap(BlitShaderType blitShaderType,
+ ShaderDimension dimension,
+ const ShaderData &shaderData,
+ const char *name);
+
+ gl::Error getBlitShader(GLenum destFormat,
+ GLenum sourceFormat,
+ bool isSigned,
+ bool unpackPremultiplyAlpha,
+ bool unpackUnmultiplyAlpha,
+ ShaderDimension dimension,
+ const Shader **shaderOut);
+ gl::Error getSwizzleShader(GLenum type,
+ D3D11_SRV_DIMENSION viewDimension,
+ const Shader **shaderOut);
+
+ gl::Error addSwizzleShaderToMap(SwizzleShaderType swizzleShaderType,
+ ShaderDimension dimension,
+ const ShaderData &shaderData,
+ const char *name);
void clearShaderMap();
+ void releaseResolveDepthStencilResources();
+ gl::Error initResolveDepthOnly(const d3d11::Format &format, const gl::Extents &extents);
+ gl::Error initResolveDepthStencil(const gl::Extents &extents);
Renderer11 *mRenderer;
@@ -159,12 +297,12 @@ class Blit11 : angle::NonCopyable
std::map<SwizzleShaderType, Shader> mSwizzleShaderMap;
bool mResourcesInitialized;
- ID3D11Buffer *mVertexBuffer;
- ID3D11SamplerState *mPointSampler;
- ID3D11SamplerState *mLinearSampler;
- ID3D11RasterizerState *mScissorEnabledRasterizerState;
- ID3D11RasterizerState *mScissorDisabledRasterizerState;
- ID3D11DepthStencilState *mDepthStencilState;
+ d3d11::Buffer mVertexBuffer;
+ d3d11::SamplerState mPointSampler;
+ d3d11::SamplerState mLinearSampler;
+ d3d11::RasterizerState mScissorEnabledRasterizerState;
+ d3d11::RasterizerState mScissorDisabledRasterizerState;
+ d3d11::DepthStencilState mDepthStencilState;
d3d11::LazyInputLayout mQuad2DIL;
d3d11::LazyShader<ID3D11VertexShader> mQuad2DVS;
@@ -176,9 +314,19 @@ class Blit11 : angle::NonCopyable
d3d11::LazyBlendState mAlphaMaskBlendState;
- ID3D11Buffer *mSwizzleCB;
+ d3d11::Buffer mSwizzleCB;
+
+ d3d11::LazyShader<ID3D11VertexShader> mResolveDepthStencilVS;
+ d3d11::LazyShader<ID3D11PixelShader> mResolveDepthPS;
+ d3d11::LazyShader<ID3D11PixelShader> mResolveDepthStencilPS;
+ d3d11::LazyShader<ID3D11PixelShader> mResolveStencilPS;
+ d3d11::ShaderResourceView mStencilSRV;
+ TextureHelper11 mResolvedDepthStencil;
+ d3d11::RenderTargetView mResolvedDepthStencilRTView;
+ TextureHelper11 mResolvedDepth;
+ d3d11::DepthStencilView mResolvedDepthDSView;
};
-}
+} // namespace rx
-#endif // LIBANGLE_RENDERER_D3D_D3D11_BLIT11_H_
+#endif // LIBANGLE_RENDERER_D3D_D3D11_BLIT11_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Buffer11.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Buffer11.cpp
index 0d5dc08b03..2317c9abdb 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Buffer11.cpp
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Buffer11.cpp
@@ -13,10 +13,14 @@
#include "common/MemoryBuffer.h"
#include "libANGLE/renderer/d3d/IndexDataManager.h"
#include "libANGLE/renderer/d3d/VertexDataManager.h"
-#include "libANGLE/renderer/d3d/d3d11/Renderer11.h"
#include "libANGLE/renderer/d3d/d3d11/RenderTarget11.h"
-#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
+#include "libANGLE/renderer/d3d/d3d11/Renderer11.h"
#include "libANGLE/renderer/d3d/d3d11/formatutils11.h"
+#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
+#include "libANGLE/renderer/renderer_utils.h"
+
+namespace rx
+{
namespace
{
@@ -27,41 +31,41 @@ GLuint ReadIndexValueFromIndices(const uint8_t *data, size_t index)
return reinterpret_cast<const T *>(data)[index];
}
typedef GLuint (*ReadIndexValueFunction)(const uint8_t *data, size_t index);
-}
-
-#if defined(ANGLE_MINGW32_COMPAT)
-typedef enum D3D11_MAP_FLAG {
- D3D11_MAP_FLAG_DO_NOT_WAIT = 0x100000
-} D3D11_MAP_FLAG;
-#endif
-namespace rx
-{
-PackPixelsParams::PackPixelsParams()
- : format(GL_NONE), type(GL_NONE), outputPitch(0), packBuffer(nullptr), offset(0)
+enum class CopyResult
{
-}
+ RECREATED,
+ NOT_RECREATED,
+};
-PackPixelsParams::PackPixelsParams(const gl::Rectangle &areaIn,
- GLenum formatIn,
- GLenum typeIn,
- GLuint outputPitchIn,
- const gl::PixelPackState &packIn,
- ptrdiff_t offsetIn)
- : area(areaIn),
- format(formatIn),
- type(typeIn),
- outputPitch(outputPitchIn),
- packBuffer(packIn.pixelBuffer.get()),
- pack(packIn.alignment, packIn.reverseRowOrder),
- offset(offsetIn)
+void CalculateConstantBufferParams(GLintptr offset,
+ GLsizeiptr size,
+ UINT *outFirstConstant,
+ UINT *outNumConstants)
{
+ // The offset must be aligned to 256 bytes (should have been enforced by glBindBufferRange).
+ ASSERT(offset % 256 == 0);
+
+ // firstConstant and numConstants are expressed in constants of 16-bytes. Furthermore they must
+ // be a multiple of 16 constants.
+ *outFirstConstant = static_cast<UINT>(offset / 16);
+
+ // The GL size is not required to be aligned to a 256 bytes boundary.
+ // Round the size up to a 256 bytes boundary then express the results in constants of 16-bytes.
+ *outNumConstants = static_cast<UINT>(rx::roundUp(size, static_cast<GLsizeiptr>(256)) / 16);
+
+ // Since the size is rounded up, firstConstant + numConstants may be bigger than the actual size
+ // of the buffer. This behaviour is explictly allowed according to the documentation on
+ // ID3D11DeviceContext1::PSSetConstantBuffers1
+ // https://msdn.microsoft.com/en-us/library/windows/desktop/hh404649%28v=vs.85%29.aspx
}
+} // anonymous namespace
+
namespace gl_d3d11
{
-D3D11_MAP GetD3DMapTypeFromBits(GLbitfield access)
+D3D11_MAP GetD3DMapTypeFromBits(BufferUsage usage, GLbitfield access)
{
bool readBit = ((access & GL_MAP_READ_BIT) != 0);
bool writeBit = ((access & GL_MAP_WRITE_BIT) != 0);
@@ -77,7 +81,8 @@ D3D11_MAP GetD3DMapTypeFromBits(GLbitfield access)
}
else if (writeBit && !readBit)
{
- return D3D11_MAP_WRITE;
+ // Special case for uniform storage - we only allow full buffer updates.
+ return usage == BUFFER_USAGE_UNIFORM ? D3D11_MAP_WRITE_DISCARD : D3D11_MAP_WRITE;
}
else if (writeBit && readBit)
{
@@ -89,7 +94,7 @@ D3D11_MAP GetD3DMapTypeFromBits(GLbitfield access)
return D3D11_MAP_READ;
}
}
-}
+} // namespace gl_d3d11
// Each instance of Buffer11::BufferStorage is specialized for a class of D3D binding points
// - vertex/transform feedback buffers
@@ -106,16 +111,22 @@ class Buffer11::BufferStorage : angle::NonCopyable
size_t getSize() const { return mBufferSize; }
void setDataRevision(DataRevision rev) { mRevision = rev; }
- virtual bool isMappable() const = 0;
+ virtual bool isCPUAccessible(GLbitfield access) const = 0;
+
+ virtual bool isGPUAccessible() const = 0;
- virtual bool copyFromStorage(BufferStorage *source,
- size_t sourceOffset,
- size_t size,
- size_t destOffset) = 0;
- virtual gl::Error resize(size_t size, bool preserveData) = 0;
+ virtual gl::ErrorOrResult<CopyResult> copyFromStorage(const gl::Context *context,
+ BufferStorage *source,
+ size_t sourceOffset,
+ size_t size,
+ size_t destOffset) = 0;
+ virtual gl::Error resize(const gl::Context *context, size_t size, bool preserveData) = 0;
- virtual uint8_t *map(size_t offset, size_t length, GLbitfield access) = 0;
- virtual void unmap() = 0;
+ virtual gl::Error map(size_t offset,
+ size_t length,
+ GLbitfield access,
+ uint8_t **mapPointerOut) = 0;
+ virtual void unmap() = 0;
gl::Error setData(const uint8_t *data, size_t offset, size_t size);
@@ -133,28 +144,41 @@ class Buffer11::BufferStorage : angle::NonCopyable
class Buffer11::NativeStorage : public Buffer11::BufferStorage
{
public:
- NativeStorage(Renderer11 *renderer, BufferUsage usage);
+ NativeStorage(Renderer11 *renderer,
+ BufferUsage usage,
+ const OnBufferDataDirtyChannel *onStorageChanged);
~NativeStorage() override;
- bool isMappable() const override { return mUsage == BUFFER_USAGE_STAGING; }
+ bool isCPUAccessible(GLbitfield access) const override;
+
+ bool isGPUAccessible() const override { return true; }
- ID3D11Buffer *getNativeStorage() const { return mNativeStorage; }
- bool copyFromStorage(BufferStorage *source,
- size_t sourceOffset,
- size_t size,
- size_t destOffset) override;
- gl::Error resize(size_t size, bool preserveData) override;
+ const d3d11::Buffer &getBuffer() const { return mBuffer; }
+ gl::ErrorOrResult<CopyResult> copyFromStorage(const gl::Context *context,
+ BufferStorage *source,
+ size_t sourceOffset,
+ size_t size,
+ size_t destOffset) override;
+ gl::Error resize(const gl::Context *context, size_t size, bool preserveData) override;
- uint8_t *map(size_t offset, size_t length, GLbitfield access) override;
+ gl::Error map(size_t offset,
+ size_t length,
+ GLbitfield access,
+ uint8_t **mapPointerOut) override;
void unmap() override;
+ gl::ErrorOrResult<const d3d11::ShaderResourceView *> getSRVForFormat(DXGI_FORMAT srvFormat);
+
private:
- static void fillBufferDesc(D3D11_BUFFER_DESC *bufferDesc,
+ static void FillBufferDesc(D3D11_BUFFER_DESC *bufferDesc,
Renderer11 *renderer,
BufferUsage usage,
unsigned int bufferSize);
+ void clearSRVs();
- ID3D11Buffer *mNativeStorage;
+ d3d11::Buffer mBuffer;
+ const OnBufferDataDirtyChannel *mOnStorageChanged;
+ std::map<DXGI_FORMAT, d3d11::ShaderResourceView> mBufferResourceViews;
};
// A emulated indexed buffer storage represents an underlying D3D11 buffer for data
@@ -166,28 +190,32 @@ class Buffer11::EmulatedIndexedStorage : public Buffer11::BufferStorage
EmulatedIndexedStorage(Renderer11 *renderer);
~EmulatedIndexedStorage() override;
- bool isMappable() const override { return true; }
+ bool isCPUAccessible(GLbitfield access) const override { return true; }
+
+ bool isGPUAccessible() const override { return false; }
- ID3D11Buffer *getNativeStorage();
+ gl::ErrorOrResult<const d3d11::Buffer *> getBuffer(SourceIndexData *indexInfo,
+ const TranslatedAttribute &attribute,
+ GLint startVertex);
- bool copyFromStorage(BufferStorage *source,
- size_t sourceOffset,
- size_t size,
- size_t destOffset) override;
+ gl::ErrorOrResult<CopyResult> copyFromStorage(const gl::Context *context,
+ BufferStorage *source,
+ size_t sourceOffset,
+ size_t size,
+ size_t destOffset) override;
- gl::Error resize(size_t size, bool preserveData) override;
+ gl::Error resize(const gl::Context *context, size_t size, bool preserveData) override;
- uint8_t *map(size_t offset, size_t length, GLbitfield access) override;
+ gl::Error map(size_t offset,
+ size_t length,
+ GLbitfield access,
+ uint8_t **mapPointerOut) override;
void unmap() override;
- bool update(SourceIndexData *indexInfo, const TranslatedAttribute *attribute);
private:
- ID3D11Buffer *mNativeStorage; // contains expanded data for use by D3D
- MemoryBuffer mMemoryBuffer; // original data (not expanded)
- MemoryBuffer mIndicesMemoryBuffer; // indices data
- SourceIndexData mIndexInfo; // indices information
- size_t mAttributeStride; // per element stride in bytes
- size_t mAttributeOffset; // starting offset
+ d3d11::Buffer mBuffer; // contains expanded data for use by D3D
+ angle::MemoryBuffer mMemoryBuffer; // original data (not expanded)
+ angle::MemoryBuffer mIndicesMemoryBuffer; // indices data
};
// Pack storage represents internal storage for pack buffers. We implement pack buffers
@@ -198,24 +226,32 @@ class Buffer11::PackStorage : public Buffer11::BufferStorage
explicit PackStorage(Renderer11 *renderer);
~PackStorage() override;
- bool isMappable() const override { return true; }
- bool copyFromStorage(BufferStorage *source,
- size_t sourceOffset,
- size_t size,
- size_t destOffset) override;
- gl::Error resize(size_t size, bool preserveData) override;
+ bool isCPUAccessible(GLbitfield access) const override { return true; }
- uint8_t *map(size_t offset, size_t length, GLbitfield access) override;
+ bool isGPUAccessible() const override { return false; }
+
+ gl::ErrorOrResult<CopyResult> copyFromStorage(const gl::Context *context,
+ BufferStorage *source,
+ size_t sourceOffset,
+ size_t size,
+ size_t destOffset) override;
+ gl::Error resize(const gl::Context *context, size_t size, bool preserveData) override;
+
+ gl::Error map(size_t offset,
+ size_t length,
+ GLbitfield access,
+ uint8_t **mapPointerOut) override;
void unmap() override;
- gl::Error packPixels(const gl::FramebufferAttachment &readAttachment,
+ gl::Error packPixels(const gl::Context *context,
+ const gl::FramebufferAttachment &readAttachment,
const PackPixelsParams &params);
private:
gl::Error flushQueuedPackCommand();
TextureHelper11 mStagingTexture;
- MemoryBuffer mMemoryBuffer;
+ angle::MemoryBuffer mMemoryBuffer;
std::unique_ptr<PackPixelsParams> mQueuedPackCommand;
PackPixelsParams mPackParams;
bool mDataModified;
@@ -230,37 +266,46 @@ class Buffer11::SystemMemoryStorage : public Buffer11::BufferStorage
explicit SystemMemoryStorage(Renderer11 *renderer);
~SystemMemoryStorage() override {}
- bool isMappable() const override { return true; }
- bool copyFromStorage(BufferStorage *source,
- size_t sourceOffset,
- size_t size,
- size_t destOffset) override;
- gl::Error resize(size_t size, bool preserveData) override;
+ bool isCPUAccessible(GLbitfield access) const override { return true; }
+
+ bool isGPUAccessible() const override { return false; }
- uint8_t *map(size_t offset, size_t length, GLbitfield access) override;
+ gl::ErrorOrResult<CopyResult> copyFromStorage(const gl::Context *context,
+ BufferStorage *source,
+ size_t sourceOffset,
+ size_t size,
+ size_t destOffset) override;
+ gl::Error resize(const gl::Context *context, size_t size, bool preserveData) override;
+
+ gl::Error map(size_t offset,
+ size_t length,
+ GLbitfield access,
+ uint8_t **mapPointerOut) override;
void unmap() override;
- MemoryBuffer *getSystemCopy() { return &mSystemCopy; }
+ angle::MemoryBuffer *getSystemCopy() { return &mSystemCopy; }
protected:
- MemoryBuffer mSystemCopy;
+ angle::MemoryBuffer mSystemCopy;
};
-Buffer11::Buffer11(Renderer11 *renderer)
- : BufferD3D(renderer),
+Buffer11::Buffer11(const gl::BufferState &state, Renderer11 *renderer)
+ : BufferD3D(state, renderer),
mRenderer(renderer),
mSize(0),
mMappedStorage(nullptr),
- mBufferStorages(BUFFER_USAGE_COUNT, nullptr),
+ mBufferStorages({}),
+ mLatestBufferStorage(nullptr),
+ mDeallocThresholds({}),
+ mIdleness({}),
mConstantBufferStorageAdditionalSize(0),
- mMaxConstantBufferLruCount(0),
- mReadUsageCount(0)
+ mMaxConstantBufferLruCount(0)
{
}
Buffer11::~Buffer11()
{
- for (auto &storage : mBufferStorages)
+ for (BufferStorage *&storage : mBufferStorages)
{
SafeDelete(storage);
}
@@ -273,79 +318,74 @@ Buffer11::~Buffer11()
mRenderer->onBufferDelete(this);
}
-gl::Error Buffer11::setData(const void *data, size_t size, GLenum usage)
+gl::Error Buffer11::setData(const gl::Context *context,
+ gl::BufferBinding target,
+ const void *data,
+ size_t size,
+ gl::BufferUsage usage)
{
- gl::Error error = setSubData(data, size, 0);
- if (error.isError())
- {
- return error;
- }
-
- updateD3DBufferUsage(usage);
- return error;
+ updateD3DBufferUsage(context, usage);
+ ANGLE_TRY(setSubData(context, target, data, size, 0));
+ return gl::NoError();
}
-gl::Error Buffer11::getData(const uint8_t **outData)
+gl::Error Buffer11::getData(const gl::Context *context, const uint8_t **outData)
{
SystemMemoryStorage *systemMemoryStorage = nullptr;
- gl::Error error = getSystemMemoryStorage(&systemMemoryStorage);
-
- if (error.isError())
- {
- *outData = nullptr;
- return error;
- }
-
- mReadUsageCount = 0;
+ ANGLE_TRY_RESULT(getSystemMemoryStorage(context), systemMemoryStorage);
ASSERT(systemMemoryStorage->getSize() >= mSize);
*outData = systemMemoryStorage->getSystemCopy()->data();
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error Buffer11::getSystemMemoryStorage(SystemMemoryStorage **storageOut)
+gl::ErrorOrResult<Buffer11::SystemMemoryStorage *> Buffer11::getSystemMemoryStorage(
+ const gl::Context *context)
{
- BufferStorage *memStorageUntyped = getBufferStorage(BUFFER_USAGE_SYSTEM_MEMORY);
-
- if (memStorageUntyped == nullptr)
- {
- // TODO(jmadill): convert all to errors
- return gl::Error(GL_OUT_OF_MEMORY);
- }
-
- *storageOut = GetAs<SystemMemoryStorage>(memStorageUntyped);
- return gl::Error(GL_NO_ERROR);
+ BufferStorage *storage = nullptr;
+ ANGLE_TRY_RESULT(getBufferStorage(context, BUFFER_USAGE_SYSTEM_MEMORY), storage);
+ return GetAs<SystemMemoryStorage>(storage);
}
-gl::Error Buffer11::setSubData(const void *data, size_t size, size_t offset)
+gl::Error Buffer11::setSubData(const gl::Context *context,
+ gl::BufferBinding target,
+ const void *data,
+ size_t size,
+ size_t offset)
{
size_t requiredSize = size + offset;
if (data && size > 0)
{
// Use system memory storage for dynamic buffers.
-
+ // Try using a constant storage for constant buffers
BufferStorage *writeBuffer = nullptr;
- if (supportsDirectBinding())
+ if (target == gl::BufferBinding::Uniform)
{
- writeBuffer = getStagingStorage();
-
- if (!writeBuffer)
+ // If we are a very large uniform buffer, keep system memory storage around so that we
+ // aren't forced to read back from a constant buffer. We also check the workaround for
+ // Intel - this requires us to use system memory so we don't end up having to copy from
+ // a constant buffer to a staging buffer.
+ // TODO(jmadill): Use Context caps.
+ if (offset == 0 && size >= mSize &&
+ size <= static_cast<UINT>(mRenderer->getNativeCaps().maxUniformBlockSize) &&
+ !mRenderer->getWorkarounds().useSystemMemoryForConstantBuffers)
+ {
+ ANGLE_TRY_RESULT(getBufferStorage(context, BUFFER_USAGE_UNIFORM), writeBuffer);
+ }
+ else
{
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to allocate internal buffer.");
+ ANGLE_TRY_RESULT(getSystemMemoryStorage(context), writeBuffer);
}
}
+ else if (supportsDirectBinding())
+ {
+ ANGLE_TRY_RESULT(getStagingStorage(context), writeBuffer);
+ }
else
{
- SystemMemoryStorage *systemMemoryStorage = nullptr;
- gl::Error error = getSystemMemoryStorage(&systemMemoryStorage);
- if (error.isError())
- {
- return error;
- }
-
- writeBuffer = systemMemoryStorage;
+ ANGLE_TRY_RESULT(getSystemMemoryStorage(context), writeBuffer);
}
ASSERT(writeBuffer);
@@ -355,24 +395,25 @@ gl::Error Buffer11::setSubData(const void *data, size_t size, size_t offset)
if (writeBuffer->getSize() < requiredSize)
{
bool preserveData = (offset > 0);
- gl::Error error = writeBuffer->resize(requiredSize, preserveData);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(writeBuffer->resize(context, requiredSize, preserveData));
}
- writeBuffer->setData(static_cast<const uint8_t *>(data), offset, size);
- writeBuffer->setDataRevision(writeBuffer->getDataRevision() + 1);
+ ANGLE_TRY(writeBuffer->setData(static_cast<const uint8_t *>(data), offset, size));
+ onStorageUpdate(writeBuffer);
+
+ // Notify any vertex arrays that we have dirty data.
+ // TODO(jmadill): Use a more fine grained notification for data updates.
+ mDirectBroadcastChannel.signal(context);
}
mSize = std::max(mSize, requiredSize);
- invalidateStaticData(D3D_BUFFER_INVALIDATE_WHOLE_CACHE);
+ invalidateStaticData(context);
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error Buffer11::copySubData(BufferImpl *source,
+gl::Error Buffer11::copySubData(const gl::Context *context,
+ BufferImpl *source,
GLintptr sourceOffset,
GLintptr destOffset,
GLsizeiptr size)
@@ -380,28 +421,32 @@ gl::Error Buffer11::copySubData(BufferImpl *source,
Buffer11 *sourceBuffer = GetAs<Buffer11>(source);
ASSERT(sourceBuffer != nullptr);
- BufferStorage *copyDest = getLatestBufferStorage();
+ BufferStorage *copyDest = nullptr;
+ ANGLE_TRY_RESULT(getLatestBufferStorage(context), copyDest);
+
if (!copyDest)
{
- copyDest = getStagingStorage();
+ ANGLE_TRY_RESULT(getStagingStorage(context), copyDest);
}
- BufferStorage *copySource = sourceBuffer->getLatestBufferStorage();
+ BufferStorage *copySource = nullptr;
+ ANGLE_TRY_RESULT(sourceBuffer->getLatestBufferStorage(context), copySource);
- if (!copySource || !copyDest)
+ if (!copySource)
{
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to allocate internal staging buffer.");
+ ANGLE_TRY_RESULT(sourceBuffer->getStagingStorage(context), copySource);
}
- // If copying to/from a pixel pack buffer, we must have a staging or
- // pack buffer partner, because other native buffers can't be mapped
- if (copyDest->getUsage() == BUFFER_USAGE_PIXEL_PACK && !copySource->isMappable())
+ ASSERT(copySource && copyDest);
+
+ // A staging buffer is needed if there is no cpu-cpu or gpu-gpu copy path avaiable.
+ if (!copyDest->isGPUAccessible() && !copySource->isCPUAccessible(GL_MAP_READ_BIT))
{
- copySource = sourceBuffer->getStagingStorage();
+ ANGLE_TRY_RESULT(sourceBuffer->getStagingStorage(context), copySource);
}
- else if (copySource->getUsage() == BUFFER_USAGE_PIXEL_PACK && !copyDest->isMappable())
+ else if (!copySource->isGPUAccessible() && !copyDest->isCPUAccessible(GL_MAP_WRITE_BIT))
{
- copyDest = getStagingStorage();
+ ANGLE_TRY_RESULT(getStagingStorage(context), copyDest);
}
// D3D11 does not allow overlapped copies until 11.1, and only if the
@@ -411,36 +456,48 @@ gl::Error Buffer11::copySubData(BufferImpl *source,
{
if (copySource->getUsage() == BUFFER_USAGE_STAGING)
{
- copySource = getBufferStorage(BUFFER_USAGE_VERTEX_OR_TRANSFORM_FEEDBACK);
+ ANGLE_TRY_RESULT(getBufferStorage(context, BUFFER_USAGE_VERTEX_OR_TRANSFORM_FEEDBACK),
+ copySource);
}
else
{
- copySource = getStagingStorage();
+ ANGLE_TRY_RESULT(getStagingStorage(context), copySource);
}
}
- copyDest->copyFromStorage(copySource, sourceOffset, size, destOffset);
- copyDest->setDataRevision(copyDest->getDataRevision() + 1);
+ CopyResult copyResult = CopyResult::NOT_RECREATED;
+ ANGLE_TRY_RESULT(copyDest->copyFromStorage(context, copySource, sourceOffset, size, destOffset),
+ copyResult);
+ onStorageUpdate(copyDest);
mSize = std::max<size_t>(mSize, destOffset + size);
- invalidateStaticData(D3D_BUFFER_INVALIDATE_WHOLE_CACHE);
+ invalidateStaticData(context);
+
+ // Also notify that direct buffers are dirty.
+ mDirectBroadcastChannel.signal(context);
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error Buffer11::map(GLenum access, GLvoid **mapPtr)
+gl::Error Buffer11::map(const gl::Context *context, GLenum access, void **mapPtr)
{
// GL_OES_mapbuffer uses an enum instead of a bitfield for it's access, convert to a bitfield
// and call mapRange.
ASSERT(access == GL_WRITE_ONLY_OES);
- return mapRange(0, mSize, GL_MAP_WRITE_BIT, mapPtr);
+ return mapRange(context, 0, mSize, GL_MAP_WRITE_BIT, mapPtr);
}
-gl::Error Buffer11::mapRange(size_t offset, size_t length, GLbitfield access, GLvoid **mapPtr)
+gl::Error Buffer11::mapRange(const gl::Context *context,
+ size_t offset,
+ size_t length,
+ GLbitfield access,
+ void **mapPtr)
{
ASSERT(!mMappedStorage);
- BufferStorage *latestStorage = getLatestBufferStorage();
+ BufferStorage *latestStorage = nullptr;
+ ANGLE_TRY_RESULT(getLatestBufferStorage(context), latestStorage);
+
if (latestStorage && (latestStorage->getUsage() == BUFFER_USAGE_PIXEL_PACK ||
latestStorage->getUsage() == BUFFER_USAGE_STAGING))
{
@@ -449,34 +506,32 @@ gl::Error Buffer11::mapRange(size_t offset, size_t length, GLbitfield access, GL
}
else
{
- // Fall back to using the staging buffer if the latest storage does
- // not exist or is not CPU-accessible.
- mMappedStorage = getStagingStorage();
+ // Fall back to using the staging buffer if the latest storage does not exist or is not
+ // CPU-accessible.
+ ANGLE_TRY_RESULT(getStagingStorage(context), mMappedStorage);
}
if (!mMappedStorage)
{
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to allocate mappable internal buffer.");
+ return gl::OutOfMemory() << "Failed to allocate mappable internal buffer.";
}
if ((access & GL_MAP_WRITE_BIT) > 0)
{
// Update the data revision immediately, since the data might be changed at any time
- mMappedStorage->setDataRevision(mMappedStorage->getDataRevision() + 1);
- invalidateStaticData(D3D_BUFFER_INVALIDATE_WHOLE_CACHE);
+ onStorageUpdate(mMappedStorage);
+ invalidateStaticData(context);
}
- uint8_t *mappedBuffer = mMappedStorage->map(offset, length, access);
- if (!mappedBuffer)
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to map internal buffer.");
- }
+ uint8_t *mappedBuffer = nullptr;
+ ANGLE_TRY(mMappedStorage->map(offset, length, access, &mappedBuffer));
+ ASSERT(mappedBuffer);
- *mapPtr = static_cast<GLvoid *>(mappedBuffer);
- return gl::Error(GL_NO_ERROR);
+ *mapPtr = static_cast<void *>(mappedBuffer);
+ return gl::NoError();
}
-gl::Error Buffer11::unmap(GLboolean *result)
+gl::Error Buffer11::unmap(const gl::Context *context, GLboolean *result)
{
ASSERT(mMappedStorage);
mMappedStorage->unmap();
@@ -485,168 +540,171 @@ gl::Error Buffer11::unmap(GLboolean *result)
// TODO: detect if we had corruption. if so, return false.
*result = GL_TRUE;
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-void Buffer11::markTransformFeedbackUsage()
+gl::Error Buffer11::markTransformFeedbackUsage(const gl::Context *context)
{
- BufferStorage *transformFeedbackStorage =
- getBufferStorage(BUFFER_USAGE_VERTEX_OR_TRANSFORM_FEEDBACK);
+ BufferStorage *transformFeedbackStorage = nullptr;
+ ANGLE_TRY_RESULT(getBufferStorage(context, BUFFER_USAGE_VERTEX_OR_TRANSFORM_FEEDBACK),
+ transformFeedbackStorage);
if (transformFeedbackStorage)
{
- transformFeedbackStorage->setDataRevision(transformFeedbackStorage->getDataRevision() + 1);
+ onStorageUpdate(transformFeedbackStorage);
}
- invalidateStaticData(D3D_BUFFER_INVALIDATE_WHOLE_CACHE);
+ invalidateStaticData(context);
+ return gl::NoError();
}
-void Buffer11::markBufferUsage()
+void Buffer11::updateDeallocThreshold(BufferUsage usage)
{
- mReadUsageCount++;
+ // The following strategy was tuned on the Oort online benchmark (http://oortonline.gl/)
+ // as well as a custom microbenchmark (IndexConversionPerfTest.Run/index_range_d3d11)
+
+ // First readback: 8 unmodified uses before we free buffer memory.
+ // After that, double the threshold each time until we reach the max.
+ if (mDeallocThresholds[usage] == 0)
+ {
+ mDeallocThresholds[usage] = 8;
+ }
+ else if (mDeallocThresholds[usage] < std::numeric_limits<unsigned int>::max() / 2u)
+ {
+ mDeallocThresholds[usage] *= 2u;
+ }
+ else
+ {
+ mDeallocThresholds[usage] = std::numeric_limits<unsigned int>::max();
+ }
+}
- // Free the system memory storage if we decide it isn't being used very often.
- const unsigned int usageLimit = 5;
+// Free the storage if we decide it isn't being used very often.
+gl::Error Buffer11::checkForDeallocation(const gl::Context *context, BufferUsage usage)
+{
+ mIdleness[usage]++;
- BufferStorage *&sysMemUsage = mBufferStorages[BUFFER_USAGE_SYSTEM_MEMORY];
- if (mReadUsageCount > usageLimit && sysMemUsage != nullptr)
+ BufferStorage *&storage = mBufferStorages[usage];
+ if (storage != nullptr && mIdleness[usage] > mDeallocThresholds[usage])
{
- if (getLatestBufferStorage() != sysMemUsage)
+ BufferStorage *latestStorage = nullptr;
+ ANGLE_TRY_RESULT(getLatestBufferStorage(context), latestStorage);
+ if (latestStorage != storage)
{
- SafeDelete(sysMemUsage);
+ SafeDelete(storage);
}
}
+
+ return gl::NoError();
}
-ID3D11Buffer *Buffer11::getBuffer(BufferUsage usage)
+// Keep system memory when we are using it for the canonical version of data.
+bool Buffer11::canDeallocateSystemMemory() const
{
- markBufferUsage();
-
- BufferStorage *bufferStorage = getBufferStorage(usage);
-
- if (!bufferStorage)
+ // Must keep system memory on Intel.
+ if (mRenderer->getWorkarounds().useSystemMemoryForConstantBuffers)
{
- // Storage out-of-memory
- return nullptr;
+ return false;
}
- return GetAs<NativeStorage>(bufferStorage)->getNativeStorage();
+ return (!mBufferStorages[BUFFER_USAGE_UNIFORM] ||
+ mSize <= mRenderer->getNativeCaps().maxUniformBlockSize);
}
-ID3D11Buffer *Buffer11::getEmulatedIndexedBuffer(SourceIndexData *indexInfo,
- const TranslatedAttribute *attribute)
+void Buffer11::markBufferUsage(BufferUsage usage)
{
- markBufferUsage();
-
- assert(indexInfo != nullptr);
- assert(attribute != nullptr);
+ mIdleness[usage] = 0;
+}
- BufferStorage *bufferStorage = getBufferStorage(BUFFER_USAGE_EMULATED_INDEXED_VERTEX);
- if (!bufferStorage)
+gl::Error Buffer11::garbageCollection(const gl::Context *context, BufferUsage currentUsage)
+{
+ if (currentUsage != BUFFER_USAGE_SYSTEM_MEMORY && canDeallocateSystemMemory())
{
- // Storage out-of-memory
- return nullptr;
+ ANGLE_TRY(checkForDeallocation(context, BUFFER_USAGE_SYSTEM_MEMORY));
}
- EmulatedIndexedStorage *emulatedStorage = GetAs<EmulatedIndexedStorage>(bufferStorage);
- if (!emulatedStorage->update(indexInfo, attribute))
+ if (currentUsage != BUFFER_USAGE_STAGING)
{
- // Storage out-of-memory
- return nullptr;
+ ANGLE_TRY(checkForDeallocation(context, BUFFER_USAGE_STAGING));
}
- return emulatedStorage->getNativeStorage();
+ return gl::NoError();
}
-ID3D11Buffer *Buffer11::getConstantBufferRange(GLintptr offset, GLsizeiptr size)
+gl::ErrorOrResult<ID3D11Buffer *> Buffer11::getBuffer(const gl::Context *context, BufferUsage usage)
{
- markBufferUsage();
+ BufferStorage *storage = nullptr;
+ ANGLE_TRY_RESULT(getBufferStorage(context, usage), storage);
+ return GetAs<NativeStorage>(storage)->getBuffer().get();
+}
- BufferStorage *bufferStorage;
+gl::ErrorOrResult<ID3D11Buffer *> Buffer11::getEmulatedIndexedBuffer(
+ const gl::Context *context,
+ SourceIndexData *indexInfo,
+ const TranslatedAttribute &attribute,
+ GLint startVertex)
+{
+ ASSERT(indexInfo);
- if (offset == 0)
- {
- bufferStorage = getBufferStorage(BUFFER_USAGE_UNIFORM);
- }
- else
- {
- bufferStorage = getConstantBufferRangeStorage(offset, size);
- }
+ BufferStorage *untypedStorage = nullptr;
+ ANGLE_TRY_RESULT(getBufferStorage(context, BUFFER_USAGE_EMULATED_INDEXED_VERTEX),
+ untypedStorage);
- if (!bufferStorage)
- {
- // Storage out-of-memory
- return nullptr;
- }
+ EmulatedIndexedStorage *emulatedStorage = GetAs<EmulatedIndexedStorage>(untypedStorage);
+
+ const d3d11::Buffer *nativeStorage = nullptr;
+ ANGLE_TRY_RESULT(emulatedStorage->getBuffer(indexInfo, attribute, startVertex), nativeStorage);
- return GetAs<NativeStorage>(bufferStorage)->getNativeStorage();
+ return nativeStorage->get();
}
-ID3D11ShaderResourceView *Buffer11::getSRV(DXGI_FORMAT srvFormat)
+gl::Error Buffer11::getConstantBufferRange(const gl::Context *context,
+ GLintptr offset,
+ GLsizeiptr size,
+ const d3d11::Buffer **bufferOut,
+ UINT *firstConstantOut,
+ UINT *numConstantsOut)
{
- BufferStorage *storage = getBufferStorage(BUFFER_USAGE_PIXEL_UNPACK);
+ BufferStorage *bufferStorage = nullptr;
- if (!storage)
+ if (offset == 0 || mRenderer->getRenderer11DeviceCaps().supportsConstantBufferOffsets)
{
- // Storage out-of-memory
- return nullptr;
+ ANGLE_TRY_RESULT(getBufferStorage(context, BUFFER_USAGE_UNIFORM), bufferStorage);
+ CalculateConstantBufferParams(offset, size, firstConstantOut, numConstantsOut);
}
-
- ID3D11Buffer *buffer = GetAs<NativeStorage>(storage)->getNativeStorage();
-
- auto bufferSRVIt = mBufferResourceViews.find(srvFormat);
-
- if (bufferSRVIt != mBufferResourceViews.end())
+ else
{
- if (bufferSRVIt->second.first == buffer)
- {
- return bufferSRVIt->second.second;
- }
- else
- {
- // The underlying buffer has changed since the SRV was created: recreate the SRV.
- SafeRelease(bufferSRVIt->second.second);
- }
+ ANGLE_TRY_RESULT(getConstantBufferRangeStorage(context, offset, size), bufferStorage);
+ *firstConstantOut = 0;
+ *numConstantsOut = 0;
}
- ID3D11Device *device = mRenderer->getDevice();
- ID3D11ShaderResourceView *bufferSRV = nullptr;
-
- const d3d11::DXGIFormat &dxgiFormatInfo = d3d11::GetDXGIFormatInfo(srvFormat);
+ *bufferOut = &GetAs<NativeStorage>(bufferStorage)->getBuffer();
- D3D11_SHADER_RESOURCE_VIEW_DESC bufferSRVDesc;
- bufferSRVDesc.Buffer.ElementOffset = 0;
- bufferSRVDesc.Buffer.ElementWidth =
- static_cast<unsigned int>(mSize) / dxgiFormatInfo.pixelBytes;
- bufferSRVDesc.ViewDimension = D3D11_SRV_DIMENSION_BUFFER;
- bufferSRVDesc.Format = srvFormat;
-
- HRESULT result = device->CreateShaderResourceView(buffer, &bufferSRVDesc, &bufferSRV);
- UNUSED_ASSERTION_VARIABLE(result);
- ASSERT(SUCCEEDED(result));
-
- mBufferResourceViews[srvFormat] = BufferSRVPair(buffer, bufferSRV);
+ return gl::NoError();
+}
- return bufferSRV;
+gl::ErrorOrResult<const d3d11::ShaderResourceView *> Buffer11::getSRV(const gl::Context *context,
+ DXGI_FORMAT srvFormat)
+{
+ BufferStorage *storage = nullptr;
+ ANGLE_TRY_RESULT(getBufferStorage(context, BUFFER_USAGE_PIXEL_UNPACK), storage);
+ NativeStorage *nativeStorage = GetAs<NativeStorage>(storage);
+ return nativeStorage->getSRVForFormat(srvFormat);
}
-gl::Error Buffer11::packPixels(const gl::FramebufferAttachment &readAttachment,
+gl::Error Buffer11::packPixels(const gl::Context *context,
+ const gl::FramebufferAttachment &readAttachment,
const PackPixelsParams &params)
{
- PackStorage *packStorage = getPackStorage();
- BufferStorage *latestStorage = getLatestBufferStorage();
+ PackStorage *packStorage = nullptr;
+ ANGLE_TRY_RESULT(getPackStorage(context), packStorage);
- if (packStorage)
- {
- gl::Error error = packStorage->packPixels(readAttachment, params);
- if (error.isError())
- {
- return error;
- }
- packStorage->setDataRevision(latestStorage ? latestStorage->getDataRevision() + 1 : 1);
- }
+ ASSERT(packStorage);
+ ANGLE_TRY(packStorage->packPixels(context, readAttachment, params));
+ onStorageUpdate(packStorage);
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
size_t Buffer11::getTotalCPUBufferMemoryBytes() const
@@ -662,48 +720,56 @@ size_t Buffer11::getTotalCPUBufferMemoryBytes() const
return allocationSize;
}
-Buffer11::BufferStorage *Buffer11::getBufferStorage(BufferUsage usage)
+gl::ErrorOrResult<Buffer11::BufferStorage *> Buffer11::getBufferStorage(const gl::Context *context,
+ BufferUsage usage)
{
ASSERT(0 <= usage && usage < BUFFER_USAGE_COUNT);
BufferStorage *&newStorage = mBufferStorages[usage];
if (!newStorage)
{
- if (usage == BUFFER_USAGE_PIXEL_PACK)
- {
- newStorage = new PackStorage(mRenderer);
- }
- else if (usage == BUFFER_USAGE_SYSTEM_MEMORY)
- {
- newStorage = new SystemMemoryStorage(mRenderer);
- }
- else if (usage == BUFFER_USAGE_EMULATED_INDEXED_VERTEX)
- {
- newStorage = new EmulatedIndexedStorage(mRenderer);
- }
- else
- {
- // buffer is not allocated, create it
- newStorage = new NativeStorage(mRenderer, usage);
- }
+ newStorage = allocateStorage(usage);
}
+ markBufferUsage(usage);
+
// resize buffer
if (newStorage->getSize() < mSize)
{
- if (newStorage->resize(mSize, true).isError())
- {
- // Out of memory error
- return nullptr;
- }
+ ANGLE_TRY(newStorage->resize(context, mSize, true));
}
- updateBufferStorage(newStorage, 0, mSize);
+ ASSERT(newStorage);
+
+ ANGLE_TRY(updateBufferStorage(context, newStorage, 0, mSize));
+ ANGLE_TRY(garbageCollection(context, usage));
return newStorage;
}
-Buffer11::BufferStorage *Buffer11::getConstantBufferRangeStorage(GLintptr offset, GLsizeiptr size)
+Buffer11::BufferStorage *Buffer11::allocateStorage(BufferUsage usage)
+{
+ updateDeallocThreshold(usage);
+ switch (usage)
+ {
+ case BUFFER_USAGE_PIXEL_PACK:
+ return new PackStorage(mRenderer);
+ case BUFFER_USAGE_SYSTEM_MEMORY:
+ return new SystemMemoryStorage(mRenderer);
+ case BUFFER_USAGE_EMULATED_INDEXED_VERTEX:
+ return new EmulatedIndexedStorage(mRenderer);
+ case BUFFER_USAGE_INDEX:
+ case BUFFER_USAGE_VERTEX_OR_TRANSFORM_FEEDBACK:
+ return new NativeStorage(mRenderer, usage, &mDirectBroadcastChannel);
+ default:
+ return new NativeStorage(mRenderer, usage, nullptr);
+ }
+}
+
+gl::ErrorOrResult<Buffer11::BufferStorage *> Buffer11::getConstantBufferRangeStorage(
+ const gl::Context *context,
+ GLintptr offset,
+ GLsizeiptr size)
{
BufferStorage *newStorage;
@@ -714,7 +780,7 @@ Buffer11::BufferStorage *Buffer11::getConstantBufferRangeStorage(GLintptr offset
if (!cacheEntry->storage)
{
- cacheEntry->storage = new NativeStorage(mRenderer, BUFFER_USAGE_UNIFORM);
+ cacheEntry->storage = allocateStorage(BUFFER_USAGE_UNIFORM);
cacheEntry->lruCount = ++mMaxConstantBufferLruCount;
}
@@ -722,6 +788,8 @@ Buffer11::BufferStorage *Buffer11::getConstantBufferRangeStorage(GLintptr offset
newStorage = cacheEntry->storage;
}
+ markBufferUsage(BUFFER_USAGE_UNIFORM);
+
if (newStorage->getSize() < static_cast<size_t>(size))
{
size_t maximumAllowedAdditionalSize = 2 * getSize();
@@ -733,8 +801,7 @@ Buffer11::BufferStorage *Buffer11::getConstantBufferRangeStorage(GLintptr offset
auto iter = std::min_element(std::begin(mConstantBufferRangeStoragesCache),
std::end(mConstantBufferRangeStoragesCache),
[](const ConstantBufferCache::value_type &a,
- const ConstantBufferCache::value_type &b)
- {
+ const ConstantBufferCache::value_type &b) {
return a.second.lruCount < b.second.lruCount;
});
@@ -746,12 +813,7 @@ Buffer11::BufferStorage *Buffer11::getConstantBufferRangeStorage(GLintptr offset
mConstantBufferRangeStoragesCache.erase(iter);
}
- if (newStorage->resize(size, false).isError())
- {
- // Out of memory error
- return nullptr;
- }
-
+ ANGLE_TRY(newStorage->resize(context, size, false));
mConstantBufferStorageAdditionalSize += sizeDelta;
// We don't copy the old data when resizing the constant buffer because the data may be
@@ -760,103 +822,148 @@ Buffer11::BufferStorage *Buffer11::getConstantBufferRangeStorage(GLintptr offset
newStorage->setDataRevision(0);
}
- updateBufferStorage(newStorage, offset, size);
-
+ ANGLE_TRY(updateBufferStorage(context, newStorage, offset, size));
+ ANGLE_TRY(garbageCollection(context, BUFFER_USAGE_UNIFORM));
return newStorage;
}
-void Buffer11::updateBufferStorage(BufferStorage *storage, size_t sourceOffset, size_t storageSize)
+gl::Error Buffer11::updateBufferStorage(const gl::Context *context,
+ BufferStorage *storage,
+ size_t sourceOffset,
+ size_t storageSize)
{
- BufferStorage *latestBuffer = getLatestBufferStorage();
- if (latestBuffer && latestBuffer->getDataRevision() > storage->getDataRevision())
- {
- // Copy through a staging buffer if we're copying from or to a non-staging, mappable
- // buffer storage. This is because we can't map a GPU buffer, and copy CPU
- // data directly. If we're already using a staging buffer we're fine.
- if (latestBuffer->getUsage() != BUFFER_USAGE_STAGING &&
- storage->getUsage() != BUFFER_USAGE_STAGING &&
- (!latestBuffer->isMappable() || !storage->isMappable()))
- {
- NativeStorage *stagingBuffer = getStagingStorage();
+ BufferStorage *latestBuffer = nullptr;
+ ANGLE_TRY_RESULT(getLatestBufferStorage(context), latestBuffer);
- stagingBuffer->copyFromStorage(latestBuffer, 0, latestBuffer->getSize(), 0);
- stagingBuffer->setDataRevision(latestBuffer->getDataRevision());
-
- latestBuffer = stagingBuffer;
- }
+ ASSERT(storage);
- // if copyFromStorage returns true, the D3D buffer has been recreated
- // and we should update our serial
- if (storage->copyFromStorage(latestBuffer, sourceOffset, storageSize, 0))
- {
- updateSerial();
- }
- storage->setDataRevision(latestBuffer->getDataRevision());
+ if (!latestBuffer)
+ {
+ onStorageUpdate(storage);
+ return gl::NoError();
}
-}
-Buffer11::BufferStorage *Buffer11::getLatestBufferStorage() const
-{
- // Even though we iterate over all the direct buffers, it is expected that only
- // 1 or 2 will be present.
- BufferStorage *latestStorage = nullptr;
- DataRevision latestRevision = 0;
- for (auto &storage : mBufferStorages)
+ if (latestBuffer->getDataRevision() <= storage->getDataRevision())
{
- if (storage && (!latestStorage || storage->getDataRevision() > latestRevision))
- {
- latestStorage = storage;
- latestRevision = storage->getDataRevision();
- }
+ return gl::NoError();
}
- // resize buffer
- if (latestStorage && latestStorage->getSize() < mSize)
+ // Copy through a staging buffer if we're copying from or to a non-staging, mappable
+ // buffer storage. This is because we can't map a GPU buffer, and copy CPU
+ // data directly. If we're already using a staging buffer we're fine.
+ if (latestBuffer->getUsage() != BUFFER_USAGE_STAGING &&
+ storage->getUsage() != BUFFER_USAGE_STAGING &&
+ (!latestBuffer->isCPUAccessible(GL_MAP_READ_BIT) ||
+ !storage->isCPUAccessible(GL_MAP_WRITE_BIT)))
{
- if (latestStorage->resize(mSize, true).isError())
- {
- // Out of memory error
- return nullptr;
- }
+ NativeStorage *stagingBuffer = nullptr;
+ ANGLE_TRY_RESULT(getStagingStorage(context), stagingBuffer);
+
+ CopyResult copyResult = CopyResult::NOT_RECREATED;
+ ANGLE_TRY_RESULT(
+ stagingBuffer->copyFromStorage(context, latestBuffer, 0, latestBuffer->getSize(), 0),
+ copyResult);
+ onCopyStorage(stagingBuffer, latestBuffer);
+
+ latestBuffer = stagingBuffer;
}
- return latestStorage;
+ CopyResult copyResult = CopyResult::NOT_RECREATED;
+ ANGLE_TRY_RESULT(storage->copyFromStorage(context, latestBuffer, sourceOffset, storageSize, 0),
+ copyResult);
+ // If the D3D buffer has been recreated, we should update our serial.
+ if (copyResult == CopyResult::RECREATED)
+ {
+ updateSerial();
+ }
+ onCopyStorage(storage, latestBuffer);
+ return gl::NoError();
}
-Buffer11::NativeStorage *Buffer11::getStagingStorage()
+gl::ErrorOrResult<Buffer11::BufferStorage *> Buffer11::getLatestBufferStorage(
+ const gl::Context *context) const
{
- BufferStorage *stagingStorage = getBufferStorage(BUFFER_USAGE_STAGING);
-
- if (!stagingStorage)
+ // resize buffer
+ if (mLatestBufferStorage && mLatestBufferStorage->getSize() < mSize)
{
- // Out-of-memory
- return nullptr;
+ ANGLE_TRY(mLatestBufferStorage->resize(context, mSize, true));
}
- return GetAs<NativeStorage>(stagingStorage);
+ return mLatestBufferStorage;
}
-Buffer11::PackStorage *Buffer11::getPackStorage()
+gl::ErrorOrResult<Buffer11::NativeStorage *> Buffer11::getStagingStorage(const gl::Context *context)
{
- BufferStorage *packStorage = getBufferStorage(BUFFER_USAGE_PIXEL_PACK);
-
- if (!packStorage)
- {
- // Out-of-memory
- return nullptr;
- }
+ BufferStorage *stagingStorage = nullptr;
+ ANGLE_TRY_RESULT(getBufferStorage(context, BUFFER_USAGE_STAGING), stagingStorage);
+ return GetAs<NativeStorage>(stagingStorage);
+}
+gl::ErrorOrResult<Buffer11::PackStorage *> Buffer11::getPackStorage(const gl::Context *context)
+{
+ BufferStorage *packStorage = nullptr;
+ ANGLE_TRY_RESULT(getBufferStorage(context, BUFFER_USAGE_PIXEL_PACK), packStorage);
return GetAs<PackStorage>(packStorage);
}
+size_t Buffer11::getSize() const
+{
+ return mSize;
+}
+
bool Buffer11::supportsDirectBinding() const
{
// Do not support direct buffers for dynamic data. The streaming buffer
// offers better performance for data which changes every frame.
- // Check for absence of static buffer interfaces to detect dynamic data.
- return (mStaticVertexBuffer && mStaticIndexBuffer);
+ return (mUsage == D3DBufferUsage::STATIC);
+}
+
+void Buffer11::initializeStaticData(const gl::Context *context)
+{
+ BufferD3D::initializeStaticData(context);
+
+ // Notify when static data changes.
+ mStaticBroadcastChannel.signal(context);
}
+void Buffer11::invalidateStaticData(const gl::Context *context)
+{
+ BufferD3D::invalidateStaticData(context);
+
+ // Notify when static data changes.
+ mStaticBroadcastChannel.signal(context);
+}
+
+OnBufferDataDirtyChannel *Buffer11::getStaticBroadcastChannel()
+{
+ return &mStaticBroadcastChannel;
+}
+
+OnBufferDataDirtyChannel *Buffer11::getDirectBroadcastChannel()
+{
+ return &mDirectBroadcastChannel;
+}
+
+void Buffer11::onCopyStorage(BufferStorage *dest, BufferStorage *source)
+{
+ ASSERT(source && mLatestBufferStorage);
+ dest->setDataRevision(source->getDataRevision());
+
+ // Only update the latest buffer storage if our usage index is lower. See comment in header.
+ if (dest->getUsage() < mLatestBufferStorage->getUsage())
+ {
+ mLatestBufferStorage = dest;
+ }
+}
+
+void Buffer11::onStorageUpdate(BufferStorage *updatedStorage)
+{
+ updatedStorage->setDataRevision(updatedStorage->getDataRevision() + 1);
+ mLatestBufferStorage = updatedStorage;
+}
+
+// Buffer11::BufferStorage implementation
+
Buffer11::BufferStorage::BufferStorage(Renderer11 *renderer, BufferUsage usage)
: mRenderer(renderer), mRevision(0), mUsage(usage), mBufferSize(0)
{
@@ -864,113 +971,118 @@ Buffer11::BufferStorage::BufferStorage(Renderer11 *renderer, BufferUsage usage)
gl::Error Buffer11::BufferStorage::setData(const uint8_t *data, size_t offset, size_t size)
{
- ASSERT(isMappable());
+ ASSERT(isCPUAccessible(GL_MAP_WRITE_BIT));
- uint8_t *writePointer = map(offset, size, GL_MAP_WRITE_BIT);
- if (!writePointer)
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to map internal buffer.");
- }
+ // Uniform storage can have a different internal size than the buffer size. Ensure we don't
+ // overflow.
+ size_t mapSize = std::min(size, mBufferSize - offset);
+
+ uint8_t *writePointer = nullptr;
+ ANGLE_TRY(map(offset, mapSize, GL_MAP_WRITE_BIT, &writePointer));
- memcpy(writePointer, data, size);
+ memcpy(writePointer, data, mapSize);
unmap();
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-Buffer11::NativeStorage::NativeStorage(Renderer11 *renderer, BufferUsage usage)
- : BufferStorage(renderer, usage), mNativeStorage(nullptr)
+// Buffer11::NativeStorage implementation
+
+Buffer11::NativeStorage::NativeStorage(Renderer11 *renderer,
+ BufferUsage usage,
+ const OnBufferDataDirtyChannel *onStorageChanged)
+ : BufferStorage(renderer, usage), mBuffer(), mOnStorageChanged(onStorageChanged)
{
}
Buffer11::NativeStorage::~NativeStorage()
{
- SafeRelease(mNativeStorage);
+ clearSRVs();
}
-// Returns true if it recreates the direct buffer
-bool Buffer11::NativeStorage::copyFromStorage(BufferStorage *source,
- size_t sourceOffset,
- size_t size,
- size_t destOffset)
+bool Buffer11::NativeStorage::isCPUAccessible(GLbitfield access) const
{
- ID3D11DeviceContext *context = mRenderer->getDeviceContext();
+ if ((access & GL_MAP_READ_BIT) != 0)
+ {
+ // Read is more exclusive than write mappability.
+ return (mUsage == BUFFER_USAGE_STAGING);
+ }
+ ASSERT((access & GL_MAP_WRITE_BIT) != 0);
+ return (mUsage == BUFFER_USAGE_STAGING || mUsage == BUFFER_USAGE_UNIFORM);
+}
+// Returns true if it recreates the direct buffer
+gl::ErrorOrResult<CopyResult> Buffer11::NativeStorage::copyFromStorage(const gl::Context *context,
+ BufferStorage *source,
+ size_t sourceOffset,
+ size_t size,
+ size_t destOffset)
+{
size_t requiredSize = destOffset + size;
- bool createBuffer = !mNativeStorage || mBufferSize < requiredSize;
+ bool createBuffer = !mBuffer.valid() || mBufferSize < requiredSize;
// (Re)initialize D3D buffer if needed
+ bool preserveData = (destOffset > 0);
if (createBuffer)
{
- bool preserveData = (destOffset > 0);
- resize(requiredSize, preserveData);
+ ANGLE_TRY(resize(context, requiredSize, preserveData));
+ }
+
+ size_t clampedSize = size;
+ if (mUsage == BUFFER_USAGE_UNIFORM)
+ {
+ clampedSize = std::min(clampedSize, mBufferSize - destOffset);
}
if (source->getUsage() == BUFFER_USAGE_PIXEL_PACK ||
source->getUsage() == BUFFER_USAGE_SYSTEM_MEMORY)
{
- ASSERT(source->isMappable());
-
- uint8_t *sourcePointer = source->map(sourceOffset, size, GL_MAP_READ_BIT);
-
- D3D11_MAPPED_SUBRESOURCE mappedResource;
- HRESULT hr = context->Map(mNativeStorage, 0, D3D11_MAP_WRITE, 0, &mappedResource);
- ASSERT(SUCCEEDED(hr));
- if (FAILED(hr))
- {
- source->unmap();
- return false;
- }
+ ASSERT(source->isCPUAccessible(GL_MAP_READ_BIT) && isCPUAccessible(GL_MAP_WRITE_BIT));
- uint8_t *destPointer = static_cast<uint8_t *>(mappedResource.pData) + destOffset;
+ // Uniform buffers must be mapped with write/discard.
+ ASSERT(!(preserveData && mUsage == BUFFER_USAGE_UNIFORM));
- // Offset bounds are validated at the API layer
- ASSERT(sourceOffset + size <= destOffset + mBufferSize);
- memcpy(destPointer, sourcePointer, size);
+ uint8_t *sourcePointer = nullptr;
+ ANGLE_TRY(source->map(sourceOffset, clampedSize, GL_MAP_READ_BIT, &sourcePointer));
- context->Unmap(mNativeStorage, 0);
+ auto err = setData(sourcePointer, destOffset, clampedSize);
source->unmap();
+ ANGLE_TRY(err);
}
else
{
D3D11_BOX srcBox;
srcBox.left = static_cast<unsigned int>(sourceOffset);
- srcBox.right = static_cast<unsigned int>(sourceOffset + size);
+ srcBox.right = static_cast<unsigned int>(sourceOffset + clampedSize);
srcBox.top = 0;
srcBox.bottom = 1;
srcBox.front = 0;
srcBox.back = 1;
- ID3D11Buffer *sourceBuffer = GetAs<NativeStorage>(source)->getNativeStorage();
+ const d3d11::Buffer *sourceBuffer = &GetAs<NativeStorage>(source)->getBuffer();
- context->CopySubresourceRegion(mNativeStorage, 0, static_cast<unsigned int>(destOffset), 0,
- 0, sourceBuffer, 0, &srcBox);
+ ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
+ deviceContext->CopySubresourceRegion(mBuffer.get(), 0,
+ static_cast<unsigned int>(destOffset), 0, 0,
+ sourceBuffer->get(), 0, &srcBox);
}
- return createBuffer;
+ return createBuffer ? CopyResult::RECREATED : CopyResult::NOT_RECREATED;
}
-gl::Error Buffer11::NativeStorage::resize(size_t size, bool preserveData)
+gl::Error Buffer11::NativeStorage::resize(const gl::Context *context,
+ size_t size,
+ bool preserveData)
{
- ID3D11Device *device = mRenderer->getDevice();
- ID3D11DeviceContext *context = mRenderer->getDeviceContext();
-
D3D11_BUFFER_DESC bufferDesc;
- fillBufferDesc(&bufferDesc, mRenderer, mUsage, static_cast<unsigned int>(size));
-
- ID3D11Buffer *newBuffer;
- HRESULT result = device->CreateBuffer(&bufferDesc, nullptr, &newBuffer);
-
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal buffer, result: 0x%X.",
- result);
- }
+ FillBufferDesc(&bufferDesc, mRenderer, mUsage, static_cast<unsigned int>(size));
- d3d11::SetDebugName(newBuffer, "Buffer11::NativeStorage");
+ d3d11::Buffer newBuffer;
+ ANGLE_TRY(mRenderer->allocateResource(bufferDesc, &newBuffer));
+ newBuffer.setDebugName("Buffer11::NativeStorage");
- if (mNativeStorage && preserveData)
+ if (mBuffer.valid() && preserveData)
{
// We don't call resize if the buffer is big enough already.
ASSERT(mBufferSize <= size);
@@ -983,19 +1095,30 @@ gl::Error Buffer11::NativeStorage::resize(size_t size, bool preserveData)
srcBox.front = 0;
srcBox.back = 1;
- context->CopySubresourceRegion(newBuffer, 0, 0, 0, 0, mNativeStorage, 0, &srcBox);
+ ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
+ deviceContext->CopySubresourceRegion(newBuffer.get(), 0, 0, 0, 0, mBuffer.get(), 0,
+ &srcBox);
}
// No longer need the old buffer
- SafeRelease(mNativeStorage);
- mNativeStorage = newBuffer;
+ mBuffer = std::move(newBuffer);
mBufferSize = bufferDesc.ByteWidth;
- return gl::Error(GL_NO_ERROR);
+ // Free the SRVs.
+ clearSRVs();
+
+ // Notify that the storage has changed.
+ if (mOnStorageChanged)
+ {
+ mOnStorageChanged->signal(context);
+ }
+
+ return gl::NoError();
}
-void Buffer11::NativeStorage::fillBufferDesc(D3D11_BUFFER_DESC *bufferDesc,
+// static
+void Buffer11::NativeStorage::FillBufferDesc(D3D11_BUFFER_DESC *bufferDesc,
Renderer11 *renderer,
BufferUsage usage,
unsigned int bufferSize)
@@ -1030,6 +1153,13 @@ void Buffer11::NativeStorage::fillBufferDesc(D3D11_BUFFER_DESC *bufferDesc,
bufferDesc->CPUAccessFlags = 0;
break;
+ case BUFFER_USAGE_INDIRECT:
+ bufferDesc->MiscFlags = D3D11_RESOURCE_MISC_DRAWINDIRECT_ARGS;
+ bufferDesc->Usage = D3D11_USAGE_DEFAULT;
+ bufferDesc->BindFlags = 0;
+ bufferDesc->CPUAccessFlags = 0;
+ break;
+
case BUFFER_USAGE_PIXEL_UNPACK:
bufferDesc->Usage = D3D11_USAGE_DEFAULT;
bufferDesc->BindFlags = D3D11_BIND_SHADER_RESOURCE;
@@ -1044,9 +1174,12 @@ void Buffer11::NativeStorage::fillBufferDesc(D3D11_BUFFER_DESC *bufferDesc,
// Constant buffers must be of a limited size, and aligned to 16 byte boundaries
// For our purposes we ignore any buffer data past the maximum constant buffer size
bufferDesc->ByteWidth = roundUp(bufferDesc->ByteWidth, 16u);
+
+ // Note: it seems that D3D11 allows larger buffers on some platforms, but not all.
+ // (Windows 10 seems to allow larger constant buffers, but not Windows 7)
bufferDesc->ByteWidth =
std::min<UINT>(bufferDesc->ByteWidth,
- static_cast<UINT>(renderer->getRendererCaps().maxUniformBlockSize));
+ static_cast<UINT>(renderer->getNativeCaps().maxUniformBlockSize));
break;
default:
@@ -1054,67 +1187,146 @@ void Buffer11::NativeStorage::fillBufferDesc(D3D11_BUFFER_DESC *bufferDesc,
}
}
-uint8_t *Buffer11::NativeStorage::map(size_t offset, size_t length, GLbitfield access)
+gl::Error Buffer11::NativeStorage::map(size_t offset,
+ size_t length,
+ GLbitfield access,
+ uint8_t **mapPointerOut)
{
- ASSERT(mUsage == BUFFER_USAGE_STAGING);
+ ASSERT(isCPUAccessible(access));
D3D11_MAPPED_SUBRESOURCE mappedResource;
ID3D11DeviceContext *context = mRenderer->getDeviceContext();
- D3D11_MAP d3dMapType = gl_d3d11::GetD3DMapTypeFromBits(access);
- UINT d3dMapFlag = ((access & GL_MAP_UNSYNCHRONIZED_BIT) != 0 ? D3D11_MAP_FLAG_DO_NOT_WAIT : 0);
+ D3D11_MAP d3dMapType = gl_d3d11::GetD3DMapTypeFromBits(mUsage, access);
+ UINT d3dMapFlag = ((access & GL_MAP_UNSYNCHRONIZED_BIT) != 0 ? D3D11_MAP_FLAG_DO_NOT_WAIT : 0);
- HRESULT result = context->Map(mNativeStorage, 0, d3dMapType, d3dMapFlag, &mappedResource);
+ HRESULT result = context->Map(mBuffer.get(), 0, d3dMapType, d3dMapFlag, &mappedResource);
ASSERT(SUCCEEDED(result));
if (FAILED(result))
{
- return nullptr;
+ return gl::OutOfMemory() << "Failed to map native storage in Buffer11::NativeStorage::map";
}
- return static_cast<uint8_t *>(mappedResource.pData) + offset;
+ ASSERT(mappedResource.pData);
+ *mapPointerOut = static_cast<uint8_t *>(mappedResource.pData) + offset;
+ return gl::NoError();
}
void Buffer11::NativeStorage::unmap()
{
- ASSERT(mUsage == BUFFER_USAGE_STAGING);
+ ASSERT(isCPUAccessible(GL_MAP_WRITE_BIT) || isCPUAccessible(GL_MAP_READ_BIT));
ID3D11DeviceContext *context = mRenderer->getDeviceContext();
- context->Unmap(mNativeStorage, 0);
+ context->Unmap(mBuffer.get(), 0);
+}
+
+gl::ErrorOrResult<const d3d11::ShaderResourceView *> Buffer11::NativeStorage::getSRVForFormat(
+ DXGI_FORMAT srvFormat)
+{
+ auto bufferSRVIt = mBufferResourceViews.find(srvFormat);
+
+ if (bufferSRVIt != mBufferResourceViews.end())
+ {
+ return &bufferSRVIt->second;
+ }
+
+ const d3d11::DXGIFormatSize &dxgiFormatInfo = d3d11::GetDXGIFormatSizeInfo(srvFormat);
+
+ D3D11_SHADER_RESOURCE_VIEW_DESC bufferSRVDesc;
+ bufferSRVDesc.Buffer.ElementOffset = 0;
+ bufferSRVDesc.Buffer.ElementWidth = static_cast<UINT>(mBufferSize) / dxgiFormatInfo.pixelBytes;
+ bufferSRVDesc.ViewDimension = D3D11_SRV_DIMENSION_BUFFER;
+ bufferSRVDesc.Format = srvFormat;
+
+ ANGLE_TRY(mRenderer->allocateResource(bufferSRVDesc, mBuffer.get(),
+ &mBufferResourceViews[srvFormat]));
+
+ return &mBufferResourceViews[srvFormat];
+}
+
+void Buffer11::NativeStorage::clearSRVs()
+{
+ mBufferResourceViews.clear();
}
+// Buffer11::EmulatedIndexStorage implementation
+
Buffer11::EmulatedIndexedStorage::EmulatedIndexedStorage(Renderer11 *renderer)
- : BufferStorage(renderer, BUFFER_USAGE_EMULATED_INDEXED_VERTEX), mNativeStorage(nullptr)
+ : BufferStorage(renderer, BUFFER_USAGE_EMULATED_INDEXED_VERTEX), mBuffer()
{
}
Buffer11::EmulatedIndexedStorage::~EmulatedIndexedStorage()
{
- SafeRelease(mNativeStorage);
}
-ID3D11Buffer *Buffer11::EmulatedIndexedStorage::getNativeStorage()
+gl::ErrorOrResult<const d3d11::Buffer *> Buffer11::EmulatedIndexedStorage::getBuffer(
+ SourceIndexData *indexInfo,
+ const TranslatedAttribute &attribute,
+ GLint startVertex)
{
- if (!mNativeStorage)
+ // If a change in the indices applied from the last draw call is detected, then the emulated
+ // indexed buffer needs to be invalidated. After invalidation, the change detected flag should
+ // be cleared to avoid unnecessary recreation of the buffer.
+ if (!mBuffer.valid() || indexInfo->srcIndicesChanged)
+ {
+ mBuffer.reset();
+
+ // Copy the source index data. This ensures that the lifetime of the indices pointer
+ // stays with this storage until the next time we invalidate.
+ size_t indicesDataSize = 0;
+ switch (indexInfo->srcIndexType)
+ {
+ case GL_UNSIGNED_INT:
+ indicesDataSize = sizeof(GLuint) * indexInfo->srcCount;
+ break;
+ case GL_UNSIGNED_SHORT:
+ indicesDataSize = sizeof(GLushort) * indexInfo->srcCount;
+ break;
+ case GL_UNSIGNED_BYTE:
+ indicesDataSize = sizeof(GLubyte) * indexInfo->srcCount;
+ break;
+ default:
+ indicesDataSize = sizeof(GLushort) * indexInfo->srcCount;
+ break;
+ }
+
+ if (!mIndicesMemoryBuffer.resize(indicesDataSize))
+ {
+ return gl::OutOfMemory() << "Error resizing index memory buffer in "
+ "Buffer11::EmulatedIndexedStorage::getBuffer";
+ }
+
+ memcpy(mIndicesMemoryBuffer.data(), indexInfo->srcIndices, indicesDataSize);
+
+ indexInfo->srcIndicesChanged = false;
+ }
+
+ if (!mBuffer.valid())
{
+ unsigned int offset = 0;
+ ANGLE_TRY_RESULT(attribute.computeOffset(startVertex), offset);
+
// Expand the memory storage upon request and cache the results.
unsigned int expandedDataSize =
- static_cast<unsigned int>((mIndexInfo.srcCount * mAttributeStride) + mAttributeOffset);
- MemoryBuffer expandedData;
+ static_cast<unsigned int>((indexInfo->srcCount * attribute.stride) + offset);
+ angle::MemoryBuffer expandedData;
if (!expandedData.resize(expandedDataSize))
{
- return nullptr;
+ return gl::OutOfMemory()
+ << "Error resizing buffer in Buffer11::EmulatedIndexedStorage::getBuffer";
}
// Clear the contents of the allocated buffer
ZeroMemory(expandedData.data(), expandedDataSize);
uint8_t *curr = expandedData.data();
- const uint8_t *ptr = static_cast<const uint8_t *>(mIndexInfo.srcIndices);
+ const uint8_t *ptr = static_cast<const uint8_t *>(indexInfo->srcIndices);
// Ensure that we start in the correct place for the emulated data copy operation to
// maintain offset behaviors.
- curr += mAttributeOffset;
+ curr += offset;
ReadIndexValueFunction readIndexValue = ReadIndexValueFromIndices<GLushort>;
- switch (mIndexInfo.srcIndexType)
+ switch (indexInfo->srcIndexType)
{
case GL_UNSIGNED_INT:
readIndexValue = ReadIndexValueFromIndices<GLuint>;
@@ -1128,17 +1340,15 @@ ID3D11Buffer *Buffer11::EmulatedIndexedStorage::getNativeStorage()
}
// Iterate over the cached index data and copy entries indicated into the emulated buffer.
- for (GLuint i = 0; i < mIndexInfo.srcCount; i++)
+ for (GLuint i = 0; i < indexInfo->srcCount; i++)
{
GLuint idx = readIndexValue(ptr, i);
- memcpy(curr, mMemoryBuffer.data() + (mAttributeStride * idx), mAttributeStride);
- curr += mAttributeStride;
+ memcpy(curr, mMemoryBuffer.data() + (attribute.stride * idx), attribute.stride);
+ curr += attribute.stride;
}
// Finally, initialize the emulated indexed native storage object with the newly copied data
// and free the temporary buffers used.
- ID3D11Device *device = mRenderer->getDevice();
-
D3D11_BUFFER_DESC bufferDesc;
bufferDesc.ByteWidth = expandedDataSize;
bufferDesc.MiscFlags = 0;
@@ -1149,99 +1359,53 @@ ID3D11Buffer *Buffer11::EmulatedIndexedStorage::getNativeStorage()
D3D11_SUBRESOURCE_DATA subResourceData = {expandedData.data(), 0, 0};
- HRESULT result = device->CreateBuffer(&bufferDesc, &subResourceData, &mNativeStorage);
- if (FAILED(result))
- {
- ERR("Could not create emulated index data buffer: %08lX", result);
- return nullptr;
- }
- d3d11::SetDebugName(mNativeStorage, "Buffer11::EmulatedIndexedStorage");
+ ANGLE_TRY(mRenderer->allocateResource(bufferDesc, &subResourceData, &mBuffer));
+ mBuffer.setDebugName("Buffer11::EmulatedIndexedStorage");
}
- return mNativeStorage;
-}
-
-bool Buffer11::EmulatedIndexedStorage::update(SourceIndexData *indexInfo,
- const TranslatedAttribute *attribute)
-{
- // If a change in the indices applied from the last draw call is detected, then the emulated
- // indexed buffer needs to be invalidated. After invalidation, the change detected flag should
- // be cleared to avoid unnecessary recreation of the buffer.
- if (mNativeStorage == nullptr || indexInfo->srcIndicesChanged)
- {
- SafeRelease(mNativeStorage);
-
- // Copy attribute offset and stride information
- mAttributeStride = attribute->stride;
- mAttributeOffset = attribute->offset;
-
- // Copy the source index data. This ensures that the lifetime of the indices pointer
- // stays with this storage until the next time we invalidate.
- size_t indicesDataSize = 0;
- switch (indexInfo->srcIndexType)
- {
- case GL_UNSIGNED_INT:
- indicesDataSize = sizeof(GLuint) * indexInfo->srcCount;
- break;
- case GL_UNSIGNED_SHORT:
- indicesDataSize = sizeof(GLushort) * indexInfo->srcCount;
- break;
- case GL_UNSIGNED_BYTE:
- indicesDataSize = sizeof(GLubyte) * indexInfo->srcCount;
- break;
- default:
- indicesDataSize = sizeof(GLushort) * indexInfo->srcCount;
- break;
- }
-
- if (!mIndicesMemoryBuffer.resize(indicesDataSize))
- {
- return false;
- }
-
- memcpy(mIndicesMemoryBuffer.data(), indexInfo->srcIndices, indicesDataSize);
-
- // Copy the source index data description and update the srcIndices pointer to point
- // to our cached index data.
- mIndexInfo = *indexInfo;
- mIndexInfo.srcIndices = mIndicesMemoryBuffer.data();
-
- indexInfo->srcIndicesChanged = false;
- }
- return true;
+ return &mBuffer;
}
-bool Buffer11::EmulatedIndexedStorage::copyFromStorage(BufferStorage *source,
- size_t sourceOffset,
- size_t size,
- size_t destOffset)
+gl::ErrorOrResult<CopyResult> Buffer11::EmulatedIndexedStorage::copyFromStorage(
+ const gl::Context *context,
+ BufferStorage *source,
+ size_t sourceOffset,
+ size_t size,
+ size_t destOffset)
{
- ASSERT(source->isMappable());
- const uint8_t *sourceData = source->map(sourceOffset, size, GL_MAP_READ_BIT);
+ ASSERT(source->isCPUAccessible(GL_MAP_READ_BIT));
+ uint8_t *sourceData = nullptr;
+ ANGLE_TRY(source->map(sourceOffset, size, GL_MAP_READ_BIT, &sourceData));
ASSERT(destOffset + size <= mMemoryBuffer.size());
memcpy(mMemoryBuffer.data() + destOffset, sourceData, size);
source->unmap();
- return true;
+ return CopyResult::RECREATED;
}
-gl::Error Buffer11::EmulatedIndexedStorage::resize(size_t size, bool preserveData)
+gl::Error Buffer11::EmulatedIndexedStorage::resize(const gl::Context *context,
+ size_t size,
+ bool preserveData)
{
if (mMemoryBuffer.size() < size)
{
if (!mMemoryBuffer.resize(size))
{
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to resize EmulatedIndexedStorage");
+ return gl::OutOfMemory() << "Failed to resize EmulatedIndexedStorage";
}
mBufferSize = size;
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-uint8_t *Buffer11::EmulatedIndexedStorage::map(size_t offset, size_t length, GLbitfield access)
+gl::Error Buffer11::EmulatedIndexedStorage::map(size_t offset,
+ size_t length,
+ GLbitfield access,
+ uint8_t **mapPointerOut)
{
ASSERT(!mMemoryBuffer.empty() && offset + length <= mMemoryBuffer.size());
- return mMemoryBuffer.data() + offset;
+ *mapPointerOut = mMemoryBuffer.data() + offset;
+ return gl::NoError();
}
void Buffer11::EmulatedIndexedStorage::unmap()
@@ -1249,6 +1413,8 @@ void Buffer11::EmulatedIndexedStorage::unmap()
// No-op
}
+// Buffer11::PackStorage implementation
+
Buffer11::PackStorage::PackStorage(Renderer11 *renderer)
: BufferStorage(renderer, BUFFER_USAGE_PIXEL_PACK), mStagingTexture(), mDataModified(false)
{
@@ -1258,32 +1424,42 @@ Buffer11::PackStorage::~PackStorage()
{
}
-bool Buffer11::PackStorage::copyFromStorage(BufferStorage *source,
- size_t sourceOffset,
- size_t size,
- size_t destOffset)
+gl::ErrorOrResult<CopyResult> Buffer11::PackStorage::copyFromStorage(const gl::Context *context,
+ BufferStorage *source,
+ size_t sourceOffset,
+ size_t size,
+ size_t destOffset)
{
- // We copy through a staging buffer when drawing with a pack buffer,
- // or for other cases where we access the pack buffer
- UNREACHABLE();
- return false;
+ ANGLE_TRY(flushQueuedPackCommand());
+
+ // For all use cases of pack buffers, we must copy through a readable buffer.
+ ASSERT(source->isCPUAccessible(GL_MAP_READ_BIT));
+ uint8_t *sourceData = nullptr;
+ ANGLE_TRY(source->map(sourceOffset, size, GL_MAP_READ_BIT, &sourceData));
+ ASSERT(destOffset + size <= mMemoryBuffer.size());
+ memcpy(mMemoryBuffer.data() + destOffset, sourceData, size);
+ source->unmap();
+ return CopyResult::NOT_RECREATED;
}
-gl::Error Buffer11::PackStorage::resize(size_t size, bool preserveData)
+gl::Error Buffer11::PackStorage::resize(const gl::Context *context, size_t size, bool preserveData)
{
if (size != mBufferSize)
{
if (!mMemoryBuffer.resize(size))
{
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to resize internal buffer storage.");
+ return gl::OutOfMemory() << "Failed to resize internal buffer storage.";
}
mBufferSize = size;
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-uint8_t *Buffer11::PackStorage::map(size_t offset, size_t length, GLbitfield access)
+gl::Error Buffer11::PackStorage::map(size_t offset,
+ size_t length,
+ GLbitfield access,
+ uint8_t **mapPointerOut)
{
ASSERT(offset + length <= getSize());
// TODO: fast path
@@ -1291,15 +1467,12 @@ uint8_t *Buffer11::PackStorage::map(size_t offset, size_t length, GLbitfield acc
// and if D3D packs the staging texture memory identically to how we would fill
// the pack buffer according to the current pack state.
- gl::Error error = flushQueuedPackCommand();
- if (error.isError())
- {
- return nullptr;
- }
+ ANGLE_TRY(flushQueuedPackCommand());
mDataModified = (mDataModified || (access & GL_MAP_WRITE_BIT) != 0);
- return mMemoryBuffer.data() + offset;
+ *mapPointerOut = mMemoryBuffer.data() + offset;
+ return gl::NoError();
}
void Buffer11::PackStorage::unmap()
@@ -1307,42 +1480,29 @@ void Buffer11::PackStorage::unmap()
// No-op
}
-gl::Error Buffer11::PackStorage::packPixels(const gl::FramebufferAttachment &readAttachment,
+gl::Error Buffer11::PackStorage::packPixels(const gl::Context *context,
+ const gl::FramebufferAttachment &readAttachment,
const PackPixelsParams &params)
{
- gl::Error error = flushQueuedPackCommand();
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(flushQueuedPackCommand());
RenderTarget11 *renderTarget = nullptr;
- error = readAttachment.getRenderTarget(&renderTarget);
- if (error.isError())
- {
- return error;
- }
-
- ID3D11Resource *renderTargetResource = renderTarget->getTexture();
- ASSERT(renderTargetResource);
+ ANGLE_TRY(readAttachment.getRenderTarget(context, &renderTarget));
+ const TextureHelper11 &srcTexture = renderTarget->getTexture();
+ ASSERT(srcTexture.valid());
unsigned int srcSubresource = renderTarget->getSubresourceIndex();
- TextureHelper11 srcTexture = TextureHelper11::MakeAndReference(renderTargetResource);
mQueuedPackCommand.reset(new PackPixelsParams(params));
gl::Extents srcTextureSize(params.area.width, params.area.height, 1);
- if (!mStagingTexture.getResource() || mStagingTexture.getFormat() != srcTexture.getFormat() ||
+ if (!mStagingTexture.get() || mStagingTexture.getFormat() != srcTexture.getFormat() ||
mStagingTexture.getExtents() != srcTextureSize)
{
- auto textureOrError =
- CreateStagingTexture(srcTexture.getTextureType(), srcTexture.getFormat(),
- srcTextureSize, mRenderer->getDevice());
- if (textureOrError.isError())
- {
- return textureOrError.getError();
- }
- mStagingTexture = std::move(textureOrError.getResult());
+ ANGLE_TRY_RESULT(
+ mRenderer->createStagingTexture(srcTexture.getTextureType(), srcTexture.getFormatSet(),
+ srcTextureSize, StagingAccess::READ),
+ mStagingTexture);
}
// ReadPixels from multisampled FBOs isn't supported in current GL
@@ -1357,17 +1517,17 @@ gl::Error Buffer11::PackStorage::packPixels(const gl::FramebufferAttachment &rea
// Select the correct layer from a 3D attachment
srcBox.front = 0;
- if (mStagingTexture.getTextureType() == GL_TEXTURE_3D)
+ if (mStagingTexture.is3D())
{
srcBox.front = static_cast<UINT>(readAttachment.layer());
}
srcBox.back = srcBox.front + 1;
// Asynchronous copy
- immediateContext->CopySubresourceRegion(mStagingTexture.getResource(), 0, 0, 0, 0,
- srcTexture.getResource(), srcSubresource, &srcBox);
+ immediateContext->CopySubresourceRegion(mStagingTexture.get(), 0, 0, 0, 0, srcTexture.get(),
+ srcSubresource, &srcBox);
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
gl::Error Buffer11::PackStorage::flushQueuedPackCommand()
@@ -1376,58 +1536,65 @@ gl::Error Buffer11::PackStorage::flushQueuedPackCommand()
if (mQueuedPackCommand)
{
- gl::Error error =
- mRenderer->packPixels(mStagingTexture, *mQueuedPackCommand, mMemoryBuffer.data());
+ ANGLE_TRY(
+ mRenderer->packPixels(mStagingTexture, *mQueuedPackCommand, mMemoryBuffer.data()));
mQueuedPackCommand.reset(nullptr);
- if (error.isError())
- {
- return error;
- }
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
+// Buffer11::SystemMemoryStorage implementation
+
Buffer11::SystemMemoryStorage::SystemMemoryStorage(Renderer11 *renderer)
: Buffer11::BufferStorage(renderer, BUFFER_USAGE_SYSTEM_MEMORY)
{
}
-bool Buffer11::SystemMemoryStorage::copyFromStorage(BufferStorage *source,
- size_t sourceOffset,
- size_t size,
- size_t destOffset)
+gl::ErrorOrResult<CopyResult> Buffer11::SystemMemoryStorage::copyFromStorage(
+ const gl::Context *context,
+ BufferStorage *source,
+ size_t sourceOffset,
+ size_t size,
+ size_t destOffset)
{
- ASSERT(source->isMappable());
- const uint8_t *sourceData = source->map(sourceOffset, size, GL_MAP_READ_BIT);
+ ASSERT(source->isCPUAccessible(GL_MAP_READ_BIT));
+ uint8_t *sourceData = nullptr;
+ ANGLE_TRY(source->map(sourceOffset, size, GL_MAP_READ_BIT, &sourceData));
ASSERT(destOffset + size <= mSystemCopy.size());
memcpy(mSystemCopy.data() + destOffset, sourceData, size);
source->unmap();
- return true;
+ return CopyResult::RECREATED;
}
-gl::Error Buffer11::SystemMemoryStorage::resize(size_t size, bool preserveData)
+gl::Error Buffer11::SystemMemoryStorage::resize(const gl::Context *context,
+ size_t size,
+ bool preserveData)
{
if (mSystemCopy.size() < size)
{
if (!mSystemCopy.resize(size))
{
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to resize SystemMemoryStorage");
+ return gl::OutOfMemory() << "Failed to resize SystemMemoryStorage";
}
mBufferSize = size;
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-uint8_t *Buffer11::SystemMemoryStorage::map(size_t offset, size_t length, GLbitfield access)
+gl::Error Buffer11::SystemMemoryStorage::map(size_t offset,
+ size_t length,
+ GLbitfield access,
+ uint8_t **mapPointerOut)
{
ASSERT(!mSystemCopy.empty() && offset + length <= mSystemCopy.size());
- return mSystemCopy.data() + offset;
+ *mapPointerOut = mSystemCopy.data() + offset;
+ return gl::NoError();
}
void Buffer11::SystemMemoryStorage::unmap()
{
// No-op
}
-}
+} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Buffer11.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Buffer11.h
index a748db57ae..ddbeeb90d2 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Buffer11.h
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Buffer11.h
@@ -9,10 +9,12 @@
#ifndef LIBANGLE_RENDERER_D3D_D3D11_BUFFER11_H_
#define LIBANGLE_RENDERER_D3D_D3D11_BUFFER11_H_
+#include <array>
#include <map>
#include "libANGLE/angletypes.h"
#include "libANGLE/renderer/d3d/BufferD3D.h"
+#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
namespace gl
{
@@ -21,69 +23,92 @@ class FramebufferAttachment;
namespace rx
{
+struct PackPixelsParams;
class Renderer11;
struct SourceIndexData;
struct TranslatedAttribute;
+// The order of this enum governs priority of 'getLatestBufferStorage'.
enum BufferUsage
{
+ BUFFER_USAGE_SYSTEM_MEMORY,
BUFFER_USAGE_STAGING,
BUFFER_USAGE_VERTEX_OR_TRANSFORM_FEEDBACK,
BUFFER_USAGE_INDEX,
+ // TODO: possibly share this buffer type with shader storage buffers.
+ BUFFER_USAGE_INDIRECT,
BUFFER_USAGE_PIXEL_UNPACK,
BUFFER_USAGE_PIXEL_PACK,
BUFFER_USAGE_UNIFORM,
- BUFFER_USAGE_SYSTEM_MEMORY,
BUFFER_USAGE_EMULATED_INDEXED_VERTEX,
BUFFER_USAGE_COUNT,
};
-struct PackPixelsParams
-{
- PackPixelsParams();
- PackPixelsParams(const gl::Rectangle &area, GLenum format, GLenum type, GLuint outputPitch,
- const gl::PixelPackState &pack, ptrdiff_t offset);
-
- gl::Rectangle area;
- GLenum format;
- GLenum type;
- GLuint outputPitch;
- gl::Buffer *packBuffer;
- gl::PixelPackState pack;
- ptrdiff_t offset;
-};
-
typedef size_t DataRevision;
class Buffer11 : public BufferD3D
{
public:
- Buffer11(Renderer11 *renderer);
- virtual ~Buffer11();
-
- ID3D11Buffer *getBuffer(BufferUsage usage);
- ID3D11Buffer *getEmulatedIndexedBuffer(SourceIndexData *indexInfo, const TranslatedAttribute *attribute);
- ID3D11Buffer *getConstantBufferRange(GLintptr offset, GLsizeiptr size);
- ID3D11ShaderResourceView *getSRV(DXGI_FORMAT srvFormat);
- bool isMapped() const { return mMappedStorage != NULL; }
- gl::Error packPixels(const gl::FramebufferAttachment &readAttachment,
+ Buffer11(const gl::BufferState &state, Renderer11 *renderer);
+ ~Buffer11() override;
+
+ gl::ErrorOrResult<ID3D11Buffer *> getBuffer(const gl::Context *context, BufferUsage usage);
+ gl::ErrorOrResult<ID3D11Buffer *> getEmulatedIndexedBuffer(const gl::Context *context,
+ SourceIndexData *indexInfo,
+ const TranslatedAttribute &attribute,
+ GLint startVertex);
+ gl::Error getConstantBufferRange(const gl::Context *context,
+ GLintptr offset,
+ GLsizeiptr size,
+ const d3d11::Buffer **bufferOut,
+ UINT *firstConstantOut,
+ UINT *numConstantsOut);
+ gl::ErrorOrResult<const d3d11::ShaderResourceView *> getSRV(const gl::Context *context,
+ DXGI_FORMAT srvFormat);
+ bool isMapped() const { return mMappedStorage != nullptr; }
+ gl::Error packPixels(const gl::Context *context,
+ const gl::FramebufferAttachment &readAttachment,
const PackPixelsParams &params);
size_t getTotalCPUBufferMemoryBytes() const;
// BufferD3D implementation
- virtual size_t getSize() const { return mSize; }
- virtual bool supportsDirectBinding() const;
- gl::Error getData(const uint8_t **outData) override;
+ size_t getSize() const override;
+ bool supportsDirectBinding() const override;
+ gl::Error getData(const gl::Context *context, const uint8_t **outData) override;
+ void initializeStaticData(const gl::Context *context) override;
+ void invalidateStaticData(const gl::Context *context) override;
// BufferImpl implementation
- virtual gl::Error setData(const void* data, size_t size, GLenum usage);
- virtual gl::Error setSubData(const void* data, size_t size, size_t offset);
- virtual gl::Error copySubData(BufferImpl* source, GLintptr sourceOffset, GLintptr destOffset, GLsizeiptr size);
- virtual gl::Error map(GLenum access, GLvoid **mapPtr);
- virtual gl::Error mapRange(size_t offset, size_t length, GLbitfield access, GLvoid **mapPtr);
- virtual gl::Error unmap(GLboolean *result);
- virtual void markTransformFeedbackUsage();
+ gl::Error setData(const gl::Context *context,
+ gl::BufferBinding target,
+ const void *data,
+ size_t size,
+ gl::BufferUsage usage) override;
+ gl::Error setSubData(const gl::Context *context,
+ gl::BufferBinding target,
+ const void *data,
+ size_t size,
+ size_t offset) override;
+ gl::Error copySubData(const gl::Context *context,
+ BufferImpl *source,
+ GLintptr sourceOffset,
+ GLintptr destOffset,
+ GLsizeiptr size) override;
+ gl::Error map(const gl::Context *context, GLenum access, void **mapPtr) override;
+ gl::Error mapRange(const gl::Context *context,
+ size_t offset,
+ size_t length,
+ GLbitfield access,
+ void **mapPtr) override;
+ gl::Error unmap(const gl::Context *context, GLboolean *result) override;
+ gl::Error markTransformFeedbackUsage(const gl::Context *context) override;
+
+ // We use two set of dirty events. Static buffers are marked dirty whenever
+ // data changes, because they must be re-translated. Direct buffers only need to be
+ // updated when the underlying ID3D11Buffer pointer changes - hopefully far less often.
+ OnBufferDataDirtyChannel *getStaticBroadcastChannel();
+ OnBufferDataDirtyChannel *getDirectBroadcastChannel();
private:
class BufferStorage;
@@ -92,21 +117,61 @@ class Buffer11 : public BufferD3D
class PackStorage;
class SystemMemoryStorage;
- Renderer11 *mRenderer;
- size_t mSize;
-
- BufferStorage *mMappedStorage;
-
- std::vector<BufferStorage*> mBufferStorages;
-
struct ConstantBufferCacheEntry
{
- ConstantBufferCacheEntry() : storage(nullptr), lruCount(0) { }
+ ConstantBufferCacheEntry() : storage(nullptr), lruCount(0) {}
BufferStorage *storage;
unsigned int lruCount;
};
+ void markBufferUsage(BufferUsage usage);
+ gl::Error garbageCollection(const gl::Context *context, BufferUsage currentUsage);
+ gl::ErrorOrResult<NativeStorage *> getStagingStorage(const gl::Context *context);
+ gl::ErrorOrResult<PackStorage *> getPackStorage(const gl::Context *context);
+ gl::ErrorOrResult<SystemMemoryStorage *> getSystemMemoryStorage(const gl::Context *context);
+
+ gl::Error updateBufferStorage(const gl::Context *context,
+ BufferStorage *storage,
+ size_t sourceOffset,
+ size_t storageSize);
+ gl::ErrorOrResult<BufferStorage *> getBufferStorage(const gl::Context *context,
+ BufferUsage usage);
+ gl::ErrorOrResult<BufferStorage *> getLatestBufferStorage(const gl::Context *context) const;
+
+ gl::ErrorOrResult<BufferStorage *> getConstantBufferRangeStorage(const gl::Context *context,
+ GLintptr offset,
+ GLsizeiptr size);
+
+ BufferStorage *allocateStorage(BufferUsage usage);
+ void updateDeallocThreshold(BufferUsage usage);
+
+ // Free the storage if we decide it isn't being used very often.
+ gl::Error checkForDeallocation(const gl::Context *context, BufferUsage usage);
+
+ // For some cases of uniform buffer storage, we can't deallocate system memory storage.
+ bool canDeallocateSystemMemory() const;
+
+ // Updates data revisions and latest storage.
+ void onCopyStorage(BufferStorage *dest, BufferStorage *source);
+ void onStorageUpdate(BufferStorage *updatedStorage);
+
+ Renderer11 *mRenderer;
+ size_t mSize;
+
+ BufferStorage *mMappedStorage;
+
+ // Buffer storages are sorted by usage. It's important that the latest buffer storage picks
+ // the lowest usage in the case where two storages are tied on data revision - this ensures
+ // we never do anything dangerous like map a uniform buffer over a staging or system memory
+ // copy.
+ std::array<BufferStorage *, BUFFER_USAGE_COUNT> mBufferStorages;
+ BufferStorage *mLatestBufferStorage;
+
+ // These two arrays are used to track when to free unused storage.
+ std::array<unsigned int, BUFFER_USAGE_COUNT> mDeallocThresholds;
+ std::array<unsigned int, BUFFER_USAGE_COUNT> mIdleness;
+
// Cache of D3D11 constant buffer for specific ranges of buffer data.
// This is used to emulate UBO ranges on 11.0 devices.
// Constant buffers are indexed by there start offset.
@@ -115,25 +180,10 @@ class Buffer11 : public BufferD3D
size_t mConstantBufferStorageAdditionalSize;
unsigned int mMaxConstantBufferLruCount;
- typedef std::pair<ID3D11Buffer *, ID3D11ShaderResourceView *> BufferSRVPair;
- std::map<DXGI_FORMAT, BufferSRVPair> mBufferResourceViews;
-
- unsigned int mReadUsageCount;
-
- void markBufferUsage();
- NativeStorage *getStagingStorage();
- PackStorage *getPackStorage();
- gl::Error getSystemMemoryStorage(SystemMemoryStorage **storageOut);
-
- void updateBufferStorage(BufferStorage *storage, size_t sourceOffset, size_t storageSize);
- BufferStorage *getBufferStorage(BufferUsage usage);
- BufferStorage *getLatestBufferStorage() const;
-
- BufferStorage *getConstantBufferRangeStorage(GLintptr offset, GLsizeiptr size);
-
- void invalidateEmulatedIndexedBuffer();
+ OnBufferDataDirtyChannel mStaticBroadcastChannel;
+ OnBufferDataDirtyChannel mDirectBroadcastChannel;
};
-}
+} // namespace rx
-#endif // LIBANGLE_RENDERER_D3D_D3D11_BUFFER11_H_
+#endif // LIBANGLE_RENDERER_D3D_D3D11_BUFFER11_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Clear11.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Clear11.cpp
index cd95c65d1c..f9dda0aeb4 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Clear11.cpp
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Clear11.cpp
@@ -1,4 +1,4 @@
-//
+
// Copyright (c) 2013 The ANGLE Project Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
@@ -20,624 +20,814 @@
#include "third_party/trace_event/trace_event.h"
// Precompiled shaders
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearfloat11vs.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearfloat11ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clear11_fl9vs.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clear11multiviewgs.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clear11multiviewvs.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clear11vs.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/cleardepth11ps.h"
#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearfloat11_fl9ps.h"
-
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearuint11vs.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearuint11ps.h"
-
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearsint11vs.h"
-#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearsint11ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearfloat11ps1.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearfloat11ps2.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearfloat11ps3.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearfloat11ps4.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearfloat11ps5.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearfloat11ps6.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearfloat11ps7.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearfloat11ps8.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearsint11ps1.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearsint11ps2.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearsint11ps3.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearsint11ps4.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearsint11ps5.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearsint11ps6.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearsint11ps7.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearsint11ps8.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearuint11ps1.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearuint11ps2.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearuint11ps3.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearuint11ps4.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearuint11ps5.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearuint11ps6.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearuint11ps7.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/clearuint11ps8.h"
namespace rx
{
+namespace
+{
+constexpr uint32_t g_ConstantBufferSize = sizeof(RtvDsvClearInfo<float>);
+constexpr uint32_t g_VertexSize = sizeof(d3d11::PositionVertex);
+
+// Updates color, depth and alpha components of cached CB if necessary.
+// Returns true if any constants are updated, false otherwise.
template <typename T>
-static void ApplyVertices(const gl::Extents &framebufferSize, const gl::Rectangle *scissor, const gl::Color<T> &color, float depth, void *buffer)
+bool UpdateDataCache(RtvDsvClearInfo<T> *dataCache,
+ const gl::Color<T> &color,
+ const float *zValue,
+ const uint32_t numRtvs,
+ const uint8_t writeMask)
{
- d3d11::PositionDepthColorVertex<T> *vertices = reinterpret_cast<d3d11::PositionDepthColorVertex<T>*>(buffer);
+ bool cacheDirty = false;
+
+ if (numRtvs > 0)
+ {
+ const bool writeRGB = (writeMask & ~D3D11_COLOR_WRITE_ENABLE_ALPHA) != 0;
+ if (writeRGB && memcmp(&dataCache->r, &color.red, sizeof(T) * 3) != 0)
+ {
+ dataCache->r = color.red;
+ dataCache->g = color.green;
+ dataCache->b = color.blue;
+ cacheDirty = true;
+ }
- float depthClear = gl::clamp01(depth);
- float left = -1.0f;
- float right = 1.0f;
- float top = -1.0f;
- float bottom = 1.0f;
+ const bool writeAlpha = (writeMask & D3D11_COLOR_WRITE_ENABLE_ALPHA) != 0;
+ if (writeAlpha && (dataCache->a != color.alpha))
+ {
+ dataCache->a = color.alpha;
+ cacheDirty = true;
+ }
+ }
- // Clip the quad coordinates to the scissor if needed
- if (scissor != nullptr)
+ if (zValue)
{
- left = std::max(left, (scissor->x / float(framebufferSize.width)) * 2.0f - 1.0f);
- right = std::min(right, ((scissor->x + scissor->width) / float(framebufferSize.width)) * 2.0f - 1.0f);
- top = std::max(top, ((framebufferSize.height - scissor->y - scissor->height) / float(framebufferSize.height)) * 2.0f - 1.0f);
- bottom = std::min(bottom, ((framebufferSize.height - scissor->y) / float(framebufferSize.height)) * 2.0f - 1.0f);
+ const float clampedZValue = gl::clamp01(*zValue);
+
+ if (clampedZValue != dataCache->z)
+ {
+ dataCache->z = clampedZValue;
+ cacheDirty = true;
+ }
}
- d3d11::SetPositionDepthColorVertex<T>(vertices + 0, left, bottom, depthClear, color);
- d3d11::SetPositionDepthColorVertex<T>(vertices + 1, left, top, depthClear, color);
- d3d11::SetPositionDepthColorVertex<T>(vertices + 2, right, bottom, depthClear, color);
- d3d11::SetPositionDepthColorVertex<T>(vertices + 3, right, top, depthClear, color);
+ return cacheDirty;
}
-Clear11::ClearShader::ClearShader(DXGI_FORMAT colorType,
- const char *inputLayoutName,
- const BYTE *vsByteCode,
- size_t vsSize,
- const char *vsDebugName,
- const BYTE *psByteCode,
- size_t psSize,
- const char *psDebugName)
- : inputLayout(nullptr),
- vertexShader(vsByteCode, vsSize, vsDebugName),
- pixelShader(psByteCode, psSize, psDebugName)
+bool AllOffsetsAreNonNegative(const std::vector<gl::Offset> &viewportOffsets)
{
- D3D11_INPUT_ELEMENT_DESC quadLayout[] =
+ for (size_t i = 0u; i < viewportOffsets.size(); ++i)
{
- { "POSITION", 0, DXGI_FORMAT_R32G32B32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0 },
- { "COLOR", 0, colorType, 0, 12, D3D11_INPUT_PER_VERTEX_DATA, 0 },
- };
-
- inputLayout = new d3d11::LazyInputLayout(quadLayout, 2, vsByteCode, vsSize, inputLayoutName);
+ const auto &offset = viewportOffsets[i];
+ if (offset.x < 0 || offset.y < 0)
+ {
+ return false;
+ }
+ }
+ return true;
}
-
-Clear11::ClearShader::~ClearShader()
+} // anonymous namespace
+
+#define CLEARPS(Index) \
+ d3d11::LazyShader<ID3D11PixelShader>(g_PS_Clear##Index, ArraySize(g_PS_Clear##Index), \
+ "Clear11 PS " ANGLE_STRINGIFY(Index))
+
+Clear11::ShaderManager::ShaderManager()
+ : mIl9(),
+ mVs9(g_VS_Clear_FL9, ArraySize(g_VS_Clear_FL9), "Clear11 VS FL9"),
+ mPsFloat9(g_PS_ClearFloat_FL9, ArraySize(g_PS_ClearFloat_FL9), "Clear11 PS FloatFL9"),
+ mVs(g_VS_Clear, ArraySize(g_VS_Clear), "Clear11 VS"),
+ mVsMultiview(g_VS_Multiview_Clear, ArraySize(g_VS_Multiview_Clear), "Clear11 VS Multiview"),
+ mGsMultiview(g_GS_Multiview_Clear, ArraySize(g_GS_Multiview_Clear), "Clear11 GS Multiview"),
+ mPsDepth(g_PS_ClearDepth, ArraySize(g_PS_ClearDepth), "Clear11 PS Depth"),
+ mPsFloat{{CLEARPS(Float1), CLEARPS(Float2), CLEARPS(Float3), CLEARPS(Float4), CLEARPS(Float5),
+ CLEARPS(Float6), CLEARPS(Float7), CLEARPS(Float8)}},
+ mPsUInt{{CLEARPS(Uint1), CLEARPS(Uint2), CLEARPS(Uint3), CLEARPS(Uint4), CLEARPS(Uint5),
+ CLEARPS(Uint6), CLEARPS(Uint7), CLEARPS(Uint8)}},
+ mPsSInt{{CLEARPS(Sint1), CLEARPS(Sint2), CLEARPS(Sint3), CLEARPS(Sint4), CLEARPS(Sint5),
+ CLEARPS(Sint6), CLEARPS(Sint7), CLEARPS(Sint8)}}
{
- SafeDelete(inputLayout);
- vertexShader.release();
- pixelShader.release();
}
-Clear11::Clear11(Renderer11 *renderer)
- : mRenderer(renderer),
- mClearBlendStates(StructLessThan<ClearBlendInfo>),
- mFloatClearShader(nullptr),
- mUintClearShader(nullptr),
- mIntClearShader(nullptr),
- mClearDepthStencilStates(StructLessThan<ClearDepthStencilInfo>),
- mVertexBuffer(nullptr),
- mRasterizerState(nullptr)
+#undef CLEARPS
+
+Clear11::ShaderManager::~ShaderManager()
{
- TRACE_EVENT0("gpu.angle", "Clear11::Clear11");
+}
- HRESULT result;
- ID3D11Device *device = renderer->getDevice();
+gl::Error Clear11::ShaderManager::getShadersAndLayout(Renderer11 *renderer,
+ const INT clearType,
+ const uint32_t numRTs,
+ const bool hasLayeredLayout,
+ const d3d11::InputLayout **il,
+ const d3d11::VertexShader **vs,
+ const d3d11::GeometryShader **gs,
+ const d3d11::PixelShader **ps)
+{
+ if (renderer->getRenderer11DeviceCaps().featureLevel <= D3D_FEATURE_LEVEL_9_3)
+ {
+ ASSERT(clearType == GL_FLOAT);
- D3D11_BUFFER_DESC vbDesc;
- vbDesc.ByteWidth = sizeof(d3d11::PositionDepthColorVertex<float>) * 4;
- vbDesc.Usage = D3D11_USAGE_DYNAMIC;
- vbDesc.BindFlags = D3D11_BIND_VERTEX_BUFFER;
- vbDesc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE;
- vbDesc.MiscFlags = 0;
- vbDesc.StructureByteStride = 0;
+ ANGLE_TRY(mVs9.resolve(renderer));
+ ANGLE_TRY(mPsFloat9.resolve(renderer));
- result = device->CreateBuffer(&vbDesc, nullptr, &mVertexBuffer);
- ASSERT(SUCCEEDED(result));
- d3d11::SetDebugName(mVertexBuffer, "Clear11 masked clear vertex buffer");
+ if (!mIl9.valid())
+ {
+ const D3D11_INPUT_ELEMENT_DESC ilDesc[] = {
+ {"POSITION", 0, DXGI_FORMAT_R32G32B32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0}};
- D3D11_RASTERIZER_DESC rsDesc;
- rsDesc.FillMode = D3D11_FILL_SOLID;
- rsDesc.CullMode = D3D11_CULL_NONE;
- rsDesc.FrontCounterClockwise = FALSE;
- rsDesc.DepthBias = 0;
- rsDesc.DepthBiasClamp = 0.0f;
- rsDesc.SlopeScaledDepthBias = 0.0f;
- rsDesc.DepthClipEnable = TRUE;
- rsDesc.ScissorEnable = FALSE;
- rsDesc.MultisampleEnable = FALSE;
- rsDesc.AntialiasedLineEnable = FALSE;
+ InputElementArray ilDescArray(ilDesc);
+ ShaderData vertexShader(g_VS_Clear_FL9);
- result = device->CreateRasterizerState(&rsDesc, &mRasterizerState);
- ASSERT(SUCCEEDED(result));
- d3d11::SetDebugName(mRasterizerState, "Clear11 masked clear rasterizer state");
+ ANGLE_TRY(renderer->allocateResource(ilDescArray, &vertexShader, &mIl9));
+ }
- if (mRenderer->getRenderer11DeviceCaps().featureLevel <= D3D_FEATURE_LEVEL_9_3)
+ *vs = &mVs9.getObj();
+ *gs = nullptr;
+ *il = &mIl9;
+ *ps = &mPsFloat9.getObj();
+ return gl::NoError();
+ }
+ if (!hasLayeredLayout)
{
- mFloatClearShader = new ClearShader(DXGI_FORMAT_R32G32B32A32_FLOAT,
- "Clear11 Float IL",
- g_VS_ClearFloat,
- ArraySize(g_VS_ClearFloat),
- "Clear11 Float VS",
- g_PS_ClearFloat_FL9,
- ArraySize(g_PS_ClearFloat_FL9),
- "Clear11 Float PS");
+ ANGLE_TRY(mVs.resolve(renderer));
+ *vs = &mVs.getObj();
+ *gs = nullptr;
}
else
{
- mFloatClearShader = new ClearShader(DXGI_FORMAT_R32G32B32A32_FLOAT,
- "Clear11 Float IL",
- g_VS_ClearFloat,
- ArraySize(g_VS_ClearFloat),
- "Clear11 Float VS",
- g_PS_ClearFloat,
- ArraySize(g_PS_ClearFloat),
- "Clear11 Float PS");
+ // For layered framebuffers we have to use the multi-view versions of the VS and GS.
+ ANGLE_TRY(mVsMultiview.resolve(renderer));
+ ANGLE_TRY(mGsMultiview.resolve(renderer));
+ *vs = &mVsMultiview.getObj();
+ *gs = &mGsMultiview.getObj();
+ }
+
+ *il = nullptr;
+
+ if (numRTs == 0)
+ {
+ ANGLE_TRY(mPsDepth.resolve(renderer));
+ *ps = &mPsDepth.getObj();
+ return gl::NoError();
}
- if (renderer->isES3Capable())
+ switch (clearType)
{
- mUintClearShader = new ClearShader(DXGI_FORMAT_R32G32B32A32_UINT,
- "Clear11 UINT IL",
- g_VS_ClearUint,
- ArraySize(g_VS_ClearUint),
- "Clear11 UINT VS",
- g_PS_ClearUint,
- ArraySize(g_PS_ClearUint),
- "Clear11 UINT PS");
- mIntClearShader = new ClearShader(DXGI_FORMAT_R32G32B32A32_UINT,
- "Clear11 SINT IL",
- g_VS_ClearSint,
- ArraySize(g_VS_ClearSint),
- "Clear11 SINT VS",
- g_PS_ClearSint,
- ArraySize(g_PS_ClearSint),
- "Clear11 SINT PS");
+ case GL_FLOAT:
+ ANGLE_TRY(mPsFloat[numRTs - 1].resolve(renderer));
+ *ps = &mPsFloat[numRTs - 1].getObj();
+ break;
+ case GL_UNSIGNED_INT:
+ ANGLE_TRY(mPsUInt[numRTs - 1].resolve(renderer));
+ *ps = &mPsUInt[numRTs - 1].getObj();
+ break;
+ case GL_INT:
+ ANGLE_TRY(mPsSInt[numRTs - 1].resolve(renderer));
+ *ps = &mPsSInt[numRTs - 1].getObj();
+ break;
+ default:
+ UNREACHABLE();
+ break;
}
+
+ return gl::NoError();
+}
+
+Clear11::Clear11(Renderer11 *renderer)
+ : mRenderer(renderer),
+ mResourcesInitialized(false),
+ mScissorEnabledRasterizerState(),
+ mScissorDisabledRasterizerState(),
+ mShaderManager(),
+ mConstantBuffer(),
+ mVertexBuffer(),
+ mShaderData({})
+{
}
Clear11::~Clear11()
{
- for (ClearBlendStateMap::iterator i = mClearBlendStates.begin(); i != mClearBlendStates.end(); i++)
+}
+
+gl::Error Clear11::ensureResourcesInitialized()
+{
+ if (mResourcesInitialized)
{
- SafeRelease(i->second);
+ return gl::NoError();
}
- mClearBlendStates.clear();
- SafeDelete(mFloatClearShader);
- SafeDelete(mUintClearShader);
- SafeDelete(mIntClearShader);
+ TRACE_EVENT0("gpu.angle", "Clear11::ensureResourcesInitialized");
+
+ static_assert((sizeof(RtvDsvClearInfo<float>) == sizeof(RtvDsvClearInfo<int>)),
+ "Size of rx::RtvDsvClearInfo<float> is not equal to rx::RtvDsvClearInfo<int>");
+
+ static_assert(
+ (sizeof(RtvDsvClearInfo<float>) == sizeof(RtvDsvClearInfo<uint32_t>)),
+ "Size of rx::RtvDsvClearInfo<float> is not equal to rx::RtvDsvClearInfo<uint32_t>");
- for (ClearDepthStencilStateMap::iterator i = mClearDepthStencilStates.begin(); i != mClearDepthStencilStates.end(); i++)
+ static_assert((sizeof(RtvDsvClearInfo<float>) % 16 == 0),
+ "The size of RtvDsvClearInfo<float> should be a multiple of 16bytes.");
+
+ // Create Rasterizer States
+ D3D11_RASTERIZER_DESC rsDesc;
+ rsDesc.FillMode = D3D11_FILL_SOLID;
+ rsDesc.CullMode = D3D11_CULL_NONE;
+ rsDesc.FrontCounterClockwise = FALSE;
+ rsDesc.DepthBias = 0;
+ rsDesc.DepthBiasClamp = 0.0f;
+ rsDesc.SlopeScaledDepthBias = 0.0f;
+ rsDesc.DepthClipEnable = TRUE;
+ rsDesc.ScissorEnable = FALSE;
+ rsDesc.MultisampleEnable = FALSE;
+ rsDesc.AntialiasedLineEnable = FALSE;
+
+ ANGLE_TRY(mRenderer->allocateResource(rsDesc, &mScissorDisabledRasterizerState));
+ mScissorDisabledRasterizerState.setDebugName("Clear11 Rasterizer State with scissor disabled");
+
+ rsDesc.ScissorEnable = TRUE;
+ ANGLE_TRY(mRenderer->allocateResource(rsDesc, &mScissorEnabledRasterizerState));
+ mScissorEnabledRasterizerState.setDebugName("Clear11 Rasterizer State with scissor enabled");
+
+ // Initialize Depthstencil state with defaults
+ mDepthStencilStateKey.depthTest = false;
+ mDepthStencilStateKey.depthMask = false;
+ mDepthStencilStateKey.depthFunc = GL_ALWAYS;
+ mDepthStencilStateKey.stencilWritemask = static_cast<GLuint>(-1);
+ mDepthStencilStateKey.stencilBackWritemask = static_cast<GLuint>(-1);
+ mDepthStencilStateKey.stencilBackMask = 0;
+ mDepthStencilStateKey.stencilTest = false;
+ mDepthStencilStateKey.stencilMask = 0;
+ mDepthStencilStateKey.stencilFail = GL_REPLACE;
+ mDepthStencilStateKey.stencilPassDepthFail = GL_REPLACE;
+ mDepthStencilStateKey.stencilPassDepthPass = GL_REPLACE;
+ mDepthStencilStateKey.stencilFunc = GL_ALWAYS;
+ mDepthStencilStateKey.stencilBackFail = GL_REPLACE;
+ mDepthStencilStateKey.stencilBackPassDepthFail = GL_REPLACE;
+ mDepthStencilStateKey.stencilBackPassDepthPass = GL_REPLACE;
+ mDepthStencilStateKey.stencilBackFunc = GL_ALWAYS;
+
+ // Initialize BlendStateKey with defaults
+ mBlendStateKey.blendState.blend = false;
+ mBlendStateKey.blendState.sourceBlendRGB = GL_ONE;
+ mBlendStateKey.blendState.sourceBlendAlpha = GL_ONE;
+ mBlendStateKey.blendState.destBlendRGB = GL_ZERO;
+ mBlendStateKey.blendState.destBlendAlpha = GL_ZERO;
+ mBlendStateKey.blendState.blendEquationRGB = GL_FUNC_ADD;
+ mBlendStateKey.blendState.blendEquationAlpha = GL_FUNC_ADD;
+ mBlendStateKey.blendState.sampleAlphaToCoverage = false;
+ mBlendStateKey.blendState.dither = true;
+
+ mResourcesInitialized = true;
+ return gl::NoError();
+}
+
+bool Clear11::useVertexBuffer() const
+{
+ return (mRenderer->getRenderer11DeviceCaps().featureLevel <= D3D_FEATURE_LEVEL_9_3);
+}
+
+gl::Error Clear11::ensureConstantBufferCreated()
+{
+ if (mConstantBuffer.valid())
{
- SafeRelease(i->second);
+ return gl::NoError();
}
- mClearDepthStencilStates.clear();
- SafeRelease(mVertexBuffer);
- SafeRelease(mRasterizerState);
+ // Create constant buffer for color & depth data
+
+ D3D11_BUFFER_DESC bufferDesc;
+ bufferDesc.ByteWidth = g_ConstantBufferSize;
+ bufferDesc.Usage = D3D11_USAGE_DYNAMIC;
+ bufferDesc.BindFlags = D3D11_BIND_CONSTANT_BUFFER;
+ bufferDesc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE;
+ bufferDesc.MiscFlags = 0;
+ bufferDesc.StructureByteStride = 0;
+
+ D3D11_SUBRESOURCE_DATA initialData;
+ initialData.pSysMem = &mShaderData;
+ initialData.SysMemPitch = g_ConstantBufferSize;
+ initialData.SysMemSlicePitch = g_ConstantBufferSize;
+
+ ANGLE_TRY(mRenderer->allocateResource(bufferDesc, &initialData, &mConstantBuffer));
+ mConstantBuffer.setDebugName("Clear11 Constant Buffer");
+ return gl::NoError();
}
-gl::Error Clear11::clearFramebuffer(const ClearParameters &clearParams, const gl::Framebuffer::Data &fboData)
+gl::Error Clear11::ensureVertexBufferCreated()
{
- const auto &colorAttachments = fboData.getColorAttachments();
- const auto &drawBufferStates = fboData.getDrawBufferStates();
- const auto *depthAttachment = fboData.getDepthAttachment();
- const auto *stencilAttachment = fboData.getStencilAttachment();
+ ASSERT(useVertexBuffer());
+
+ if (mVertexBuffer.valid())
+ {
+ return gl::NoError();
+ }
+
+ // Create vertex buffer with vertices for a quad covering the entire surface
+
+ static_assert((sizeof(d3d11::PositionVertex) % 16) == 0,
+ "d3d11::PositionVertex should be a multiple of 16 bytes");
+ const d3d11::PositionVertex vbData[6] = {{-1.0f, 1.0f, 0.0f, 1.0f}, {1.0f, -1.0f, 0.0f, 1.0f},
+ {-1.0f, -1.0f, 0.0f, 1.0f}, {-1.0f, 1.0f, 0.0f, 1.0f},
+ {1.0f, 1.0f, 0.0f, 1.0f}, {1.0f, -1.0f, 0.0f, 1.0f}};
+
+ const UINT vbSize = sizeof(vbData);
+
+ D3D11_BUFFER_DESC bufferDesc;
+ bufferDesc.ByteWidth = vbSize;
+ bufferDesc.Usage = D3D11_USAGE_IMMUTABLE;
+ bufferDesc.BindFlags = D3D11_BIND_VERTEX_BUFFER;
+ bufferDesc.CPUAccessFlags = 0;
+ bufferDesc.MiscFlags = 0;
+ bufferDesc.StructureByteStride = 0;
+
+ D3D11_SUBRESOURCE_DATA initialData;
+ initialData.pSysMem = vbData;
+ initialData.SysMemPitch = vbSize;
+ initialData.SysMemSlicePitch = initialData.SysMemPitch;
+
+ ANGLE_TRY(mRenderer->allocateResource(bufferDesc, &initialData, &mVertexBuffer));
+ mVertexBuffer.setDebugName("Clear11 Vertex Buffer");
+ return gl::NoError();
+}
- ASSERT(colorAttachments.size() == drawBufferStates.size());
+gl::Error Clear11::clearFramebuffer(const gl::Context *context,
+ const ClearParameters &clearParams,
+ const gl::FramebufferState &fboData)
+{
+ ANGLE_TRY(ensureResourcesInitialized());
// Iterate over the color buffers which require clearing and determine if they can be
// cleared with ID3D11DeviceContext::ClearRenderTargetView or ID3D11DeviceContext1::ClearView.
// This requires:
- // 1) The render target is being cleared to a float value (will be cast to integer when clearing integer
- // render targets as expected but does not work the other way around)
+ // 1) The render target is being cleared to a float value (will be cast to integer when clearing
+ // integer render targets as expected but does not work the other way around)
// 2) The format of the render target has no color channels that are currently masked out.
- // Clear the easy-to-clear buffers on the spot and accumulate the ones that require special work.
+ // Clear the easy-to-clear buffers on the spot and accumulate the ones that require special
+ // work.
//
// If these conditions are met, and:
// - No scissored clear is needed, then clear using ID3D11DeviceContext::ClearRenderTargetView.
// - A scissored clear is needed then clear using ID3D11DeviceContext1::ClearView if available.
- // Otherwise draw a quad.
+ // Otherwise perform a shader based clear.
//
- // Also determine if the depth stencil can be cleared with ID3D11DeviceContext::ClearDepthStencilView
- // by checking if the stencil write mask covers the entire stencil.
+ // Also determine if the DSV can be cleared withID3D11DeviceContext::ClearDepthStencilView by
+ // checking if the stencil write mask covers the entire stencil.
//
- // To clear the remaining buffers, quads must be drawn containing an int, uint or float vertex color
- // attribute.
+ // To clear the remaining buffers, a shader based clear is performed:
+ // - The appropriate ShaderManagers (VS & PS) for the clearType is set
+ // - A CB containing the clear color and Z values is bound
+ // - An IL and VB are bound (for FL93 and below)
+ // - ScissorRect/Raststate/Viewport set as required
+ // - Blendstate set containing appropriate colorMasks
+ // - DepthStencilState set with appropriate parameters for a z or stencil clear if required
+ // - Color and/or Z buffers to be cleared are bound
+ // - Primitive covering entire clear area is drawn
gl::Extents framebufferSize;
- const gl::FramebufferAttachment *colorAttachment = fboData.getFirstColorAttachment();
- if (colorAttachment != nullptr)
- {
- framebufferSize = colorAttachment->getSize();
- }
- else if (depthAttachment != nullptr)
- {
- framebufferSize = depthAttachment->getSize();
- }
- else if (stencilAttachment != nullptr)
+ const auto *depthStencilAttachment = fboData.getDepthOrStencilAttachment();
+ if (depthStencilAttachment != nullptr)
{
- framebufferSize = stencilAttachment->getSize();
+ framebufferSize = depthStencilAttachment->getSize();
}
else
{
- UNREACHABLE();
- return gl::Error(GL_INVALID_OPERATION);
+ const gl::FramebufferAttachment *colorAttachment = fboData.getFirstColorAttachment();
+
+ if (!colorAttachment)
+ {
+ UNREACHABLE();
+ return gl::InternalError();
+ }
+
+ framebufferSize = colorAttachment->getSize();
}
- if (clearParams.scissorEnabled && (clearParams.scissor.x >= framebufferSize.width ||
- clearParams.scissor.y >= framebufferSize.height ||
- clearParams.scissor.x + clearParams.scissor.width <= 0 ||
- clearParams.scissor.y + clearParams.scissor.height <= 0))
+ const bool isSideBySideFBO =
+ (fboData.getMultiviewLayout() == GL_FRAMEBUFFER_MULTIVIEW_SIDE_BY_SIDE_ANGLE);
+ bool needScissoredClear = false;
+ std::vector<D3D11_RECT> scissorRects;
+ if (clearParams.scissorEnabled)
{
- // Scissor is enabled and the scissor rectangle is outside the renderbuffer
- return gl::Error(GL_NO_ERROR);
- }
+ const std::vector<gl::Offset> *viewportOffsets = fboData.getViewportOffsets();
+ ASSERT(viewportOffsets != nullptr);
+ ASSERT(AllOffsetsAreNonNegative(*fboData.getViewportOffsets()));
- bool needScissoredClear = clearParams.scissorEnabled && (clearParams.scissor.x > 0 || clearParams.scissor.y > 0 ||
- clearParams.scissor.x + clearParams.scissor.width < framebufferSize.width ||
- clearParams.scissor.y + clearParams.scissor.height < framebufferSize.height);
+ if (clearParams.scissor.x >= framebufferSize.width ||
+ clearParams.scissor.y >= framebufferSize.height || clearParams.scissor.width == 0 ||
+ clearParams.scissor.height == 0)
+ {
+ // The check assumes that the viewport offsets are not negative as according to the
+ // ANGLE_multiview spec.
+ // Scissor rect is outside the renderbuffer or is an empty rect.
+ return gl::NoError();
+ }
- std::vector<MaskedRenderTarget> maskedClearRenderTargets;
- RenderTarget11* maskedClearDepthStencil = nullptr;
+ if (isSideBySideFBO)
+ {
+ // We always have to do a scissor clear for side-by-side framebuffers.
+ needScissoredClear = true;
+ }
+ else
+ {
+ // Because the viewport offsets can generate scissor rectangles within the framebuffer's
+ // bounds, we can do this check only for non-side-by-side framebuffers.
+ if (clearParams.scissor.x + clearParams.scissor.width <= 0 ||
+ clearParams.scissor.y + clearParams.scissor.height <= 0)
+ {
+ // Scissor rect is outside the renderbuffer.
+ return gl::NoError();
+ }
+ needScissoredClear =
+ clearParams.scissor.x > 0 || clearParams.scissor.y > 0 ||
+ clearParams.scissor.x + clearParams.scissor.width < framebufferSize.width ||
+ clearParams.scissor.y + clearParams.scissor.height < framebufferSize.height;
+ }
- ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
-#if defined(ANGLE_ENABLE_D3D11_1)
+ if (needScissoredClear)
+ {
+ // Apply viewport offsets to compute the final scissor rectangles. This is valid also
+ // for non-side-by-side framebuffers, because the default viewport offset is {0,0}.
+ const size_t numViews = viewportOffsets->size();
+ scissorRects.reserve(numViews);
+ for (size_t i = 0u; i < numViews; ++i)
+ {
+ const gl::Offset &offset = (*viewportOffsets)[i];
+ D3D11_RECT rect;
+ int x = clearParams.scissor.x + offset.x;
+ int y = clearParams.scissor.y + offset.y;
+ rect.left = x;
+ rect.right = x + clearParams.scissor.width;
+ rect.top = y;
+ rect.bottom = y + clearParams.scissor.height;
+ scissorRects.emplace_back(rect);
+ }
+ }
+ }
+
+ ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
ID3D11DeviceContext1 *deviceContext1 = mRenderer->getDeviceContext1IfSupported();
-#endif
- ID3D11Device *device = mRenderer->getDevice();
- for (size_t colorAttachmentIndex = 0; colorAttachmentIndex < colorAttachments.size();
- colorAttachmentIndex++)
+ std::array<ID3D11RenderTargetView *, D3D11_SIMULTANEOUS_RENDER_TARGET_COUNT> rtvs;
+ std::array<uint8_t, D3D11_SIMULTANEOUS_RENDER_TARGET_COUNT> rtvMasks = {};
+
+ uint32_t numRtvs = 0;
+ const uint8_t colorMask =
+ gl_d3d11::ConvertColorMask(clearParams.colorMaskRed, clearParams.colorMaskGreen,
+ clearParams.colorMaskBlue, clearParams.colorMaskAlpha);
+
+ const auto &colorAttachments = fboData.getColorAttachments();
+ for (auto colorAttachmentIndex : fboData.getEnabledDrawBuffers())
{
const gl::FramebufferAttachment &attachment = colorAttachments[colorAttachmentIndex];
- if (clearParams.clearColor[colorAttachmentIndex] && attachment.isAttached() &&
- drawBufferStates[colorAttachmentIndex] != GL_NONE)
+ if (!clearParams.clearColor[colorAttachmentIndex])
{
- RenderTarget11 *renderTarget = nullptr;
- gl::Error error = attachment.getRenderTarget(&renderTarget);
- if (error.isError())
- {
- return error;
- }
+ continue;
+ }
- const gl::InternalFormat &formatInfo = gl::GetInternalFormatInfo(attachment.getInternalFormat());
+ RenderTarget11 *renderTarget = nullptr;
+ ANGLE_TRY(attachment.getRenderTarget(context, &renderTarget));
- if (clearParams.colorClearType == GL_FLOAT &&
- !(formatInfo.componentType == GL_FLOAT || formatInfo.componentType == GL_UNSIGNED_NORMALIZED || formatInfo.componentType == GL_SIGNED_NORMALIZED))
- {
- ERR(
- "It is undefined behaviour to clear a render buffer which is not normalized "
- "fixed point or floating-"
- "point to floating point values (color attachment %u has internal format "
- "0x%X).",
- colorAttachmentIndex, attachment.getInternalFormat());
- }
+ const gl::InternalFormat &formatInfo = *attachment.getFormat().info;
- if ((formatInfo.redBits == 0 || !clearParams.colorMaskRed) &&
- (formatInfo.greenBits == 0 || !clearParams.colorMaskGreen) &&
- (formatInfo.blueBits == 0 || !clearParams.colorMaskBlue) &&
- (formatInfo.alphaBits == 0 || !clearParams.colorMaskAlpha))
- {
- // Every channel either does not exist in the render target or is masked out
- continue;
- }
- else if ((!(mRenderer->getRenderer11DeviceCaps().supportsClearView) && needScissoredClear) || clearParams.colorClearType != GL_FLOAT ||
- (formatInfo.redBits > 0 && !clearParams.colorMaskRed) ||
- (formatInfo.greenBits > 0 && !clearParams.colorMaskGreen) ||
- (formatInfo.blueBits > 0 && !clearParams.colorMaskBlue) ||
- (formatInfo.alphaBits > 0 && !clearParams.colorMaskAlpha))
- {
- // A masked clear is required, or a scissored clear is required and ID3D11DeviceContext1::ClearView is unavailable
- MaskedRenderTarget maskAndRt;
- bool clearColor = clearParams.clearColor[colorAttachmentIndex];
- maskAndRt.colorMask[0] = (clearColor && clearParams.colorMaskRed);
- maskAndRt.colorMask[1] = (clearColor && clearParams.colorMaskGreen);
- maskAndRt.colorMask[2] = (clearColor && clearParams.colorMaskBlue);
- maskAndRt.colorMask[3] = (clearColor && clearParams.colorMaskAlpha);
- maskAndRt.renderTarget = renderTarget;
- maskedClearRenderTargets.push_back(maskAndRt);
- }
- else
- {
- // ID3D11DeviceContext::ClearRenderTargetView or ID3D11DeviceContext1::ClearView is possible
+ if (clearParams.colorType == GL_FLOAT &&
+ !(formatInfo.componentType == GL_FLOAT ||
+ formatInfo.componentType == GL_UNSIGNED_NORMALIZED ||
+ formatInfo.componentType == GL_SIGNED_NORMALIZED))
+ {
+ ERR() << "It is undefined behaviour to clear a render buffer which is not "
+ "normalized fixed point or floating-point to floating point values (color "
+ "attachment "
+ << colorAttachmentIndex << " has internal format " << attachment.getFormat()
+ << ").";
+ }
- ID3D11RenderTargetView *framebufferRTV = renderTarget->getRenderTargetView();
- if (!framebufferRTV)
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Internal render target view pointer unexpectedly null.");
- }
+ if ((formatInfo.redBits == 0 || !clearParams.colorMaskRed) &&
+ (formatInfo.greenBits == 0 || !clearParams.colorMaskGreen) &&
+ (formatInfo.blueBits == 0 || !clearParams.colorMaskBlue) &&
+ (formatInfo.alphaBits == 0 || !clearParams.colorMaskAlpha))
+ {
+ // Every channel either does not exist in the render target or is masked out
+ continue;
+ }
- const d3d11::DXGIFormat &dxgiFormatInfo = d3d11::GetDXGIFormatInfo(renderTarget->getDXGIFormat());
+ const auto &framebufferRTV = renderTarget->getRenderTargetView();
+ ASSERT(framebufferRTV.valid());
- // Check if the actual format has a channel that the internal format does not and set them to the
- // default values
- float clearValues[4] =
- {
- ((formatInfo.redBits == 0 && dxgiFormatInfo.redBits > 0) ? 0.0f : clearParams.colorFClearValue.red),
- ((formatInfo.greenBits == 0 && dxgiFormatInfo.greenBits > 0) ? 0.0f : clearParams.colorFClearValue.green),
- ((formatInfo.blueBits == 0 && dxgiFormatInfo.blueBits > 0) ? 0.0f : clearParams.colorFClearValue.blue),
- ((formatInfo.alphaBits == 0 && dxgiFormatInfo.alphaBits > 0) ? 1.0f : clearParams.colorFClearValue.alpha),
- };
+ if ((!(mRenderer->getRenderer11DeviceCaps().supportsClearView) && needScissoredClear) ||
+ clearParams.colorType != GL_FLOAT ||
+ (formatInfo.redBits > 0 && !clearParams.colorMaskRed) ||
+ (formatInfo.greenBits > 0 && !clearParams.colorMaskGreen) ||
+ (formatInfo.blueBits > 0 && !clearParams.colorMaskBlue) ||
+ (formatInfo.alphaBits > 0 && !clearParams.colorMaskAlpha))
+ {
+ rtvs[numRtvs] = framebufferRTV.get();
+ rtvMasks[numRtvs] = gl_d3d11::GetColorMask(formatInfo) & colorMask;
+ numRtvs++;
+ }
+ else
+ {
+ // ID3D11DeviceContext::ClearRenderTargetView or ID3D11DeviceContext1::ClearView is
+ // possible
+
+ const auto &nativeFormat = renderTarget->getFormatSet().format();
+
+ // Check if the actual format has a channel that the internal format does not and
+ // set them to the default values
+ float clearValues[4] = {
+ ((formatInfo.redBits == 0 && nativeFormat.redBits > 0) ? 0.0f
+ : clearParams.colorF.red),
+ ((formatInfo.greenBits == 0 && nativeFormat.greenBits > 0)
+ ? 0.0f
+ : clearParams.colorF.green),
+ ((formatInfo.blueBits == 0 && nativeFormat.blueBits > 0) ? 0.0f
+ : clearParams.colorF.blue),
+ ((formatInfo.alphaBits == 0 && nativeFormat.alphaBits > 0)
+ ? 1.0f
+ : clearParams.colorF.alpha),
+ };
+
+ if (formatInfo.alphaBits == 1)
+ {
+ // Some drivers do not correctly handle calling Clear() on a format with 1-bit
+ // alpha. They can incorrectly round all non-zero values up to 1.0f. Note that
+ // WARP does not do this. We should handle the rounding for them instead.
+ clearValues[3] = (clearParams.colorF.alpha >= 0.5f) ? 1.0f : 0.0f;
+ }
- if (dxgiFormatInfo.alphaBits == 1)
+ if (needScissoredClear)
+ {
+ // We shouldn't reach here if deviceContext1 is unavailable.
+ ASSERT(deviceContext1);
+ // There must be at least one scissor rectangle.
+ ASSERT(!scissorRects.empty());
+ deviceContext1->ClearView(framebufferRTV.get(), clearValues, scissorRects.data(),
+ static_cast<UINT>(scissorRects.size()));
+ if (mRenderer->getWorkarounds().callClearTwice)
{
- // Some drivers do not correctly handle calling Clear() on a format with 1-bit alpha.
- // They can incorrectly round all non-zero values up to 1.0f. Note that WARP does not do this.
- // We should handle the rounding for them instead.
- clearValues[3] = (clearParams.colorFClearValue.alpha >= 0.5f) ? 1.0f : 0.0f;
+ deviceContext1->ClearView(framebufferRTV.get(), clearValues,
+ scissorRects.data(),
+ static_cast<UINT>(scissorRects.size()));
}
-
-#if defined(ANGLE_ENABLE_D3D11_1)
- if (needScissoredClear)
- {
- // We shouldn't reach here if deviceContext1 is unavailable.
- ASSERT(deviceContext1);
-
- D3D11_RECT rect;
- rect.left = clearParams.scissor.x;
- rect.right = clearParams.scissor.x + clearParams.scissor.width;
- rect.top = clearParams.scissor.y;
- rect.bottom = clearParams.scissor.y + clearParams.scissor.height;
-
- deviceContext1->ClearView(framebufferRTV, clearValues, &rect, 1);
- }
- else
-#endif
+ }
+ else
+ {
+ deviceContext->ClearRenderTargetView(framebufferRTV.get(), clearValues);
+ if (mRenderer->getWorkarounds().callClearTwice)
{
- deviceContext->ClearRenderTargetView(framebufferRTV, clearValues);
+ deviceContext->ClearRenderTargetView(framebufferRTV.get(), clearValues);
}
}
}
}
+ ID3D11DepthStencilView *dsv = nullptr;
+
if (clearParams.clearDepth || clearParams.clearStencil)
{
- const gl::FramebufferAttachment *attachment = (depthAttachment != nullptr) ? depthAttachment : stencilAttachment;
- ASSERT(attachment != nullptr);
+ RenderTarget11 *depthStencilRenderTarget = nullptr;
- RenderTarget11 *renderTarget = nullptr;
- gl::Error error = attachment->getRenderTarget(&renderTarget);
- if (error.isError())
- {
- return error;
- }
+ ASSERT(depthStencilAttachment != nullptr);
+ ANGLE_TRY(depthStencilAttachment->getRenderTarget(context, &depthStencilRenderTarget));
- const d3d11::DXGIFormat &dxgiFormatInfo = d3d11::GetDXGIFormatInfo(renderTarget->getDXGIFormat());
+ dsv = depthStencilRenderTarget->getDepthStencilView().get();
+ ASSERT(dsv != nullptr);
- unsigned int stencilUnmasked = (stencilAttachment != nullptr) ? (1 << dxgiFormatInfo.stencilBits) - 1 : 0;
- bool needMaskedStencilClear = clearParams.clearStencil && (clearParams.stencilWriteMask & stencilUnmasked) != stencilUnmasked;
+ const auto &nativeFormat = depthStencilRenderTarget->getFormatSet().format();
+ const auto *stencilAttachment = fboData.getStencilAttachment();
- if (needScissoredClear || needMaskedStencilClear)
- {
- maskedClearDepthStencil = renderTarget;
- }
- else
+ uint32_t stencilUnmasked =
+ (stencilAttachment != nullptr) ? (1 << nativeFormat.stencilBits) - 1 : 0;
+ bool needMaskedStencilClear =
+ clearParams.clearStencil &&
+ (clearParams.stencilWriteMask & stencilUnmasked) != stencilUnmasked;
+
+ if (!needScissoredClear && !needMaskedStencilClear)
{
- ID3D11DepthStencilView *framebufferDSV = renderTarget->getDepthStencilView();
- if (!framebufferDSV)
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Internal depth stencil view pointer unexpectedly null.");
- }
+ const UINT clearFlags = (clearParams.clearDepth ? D3D11_CLEAR_DEPTH : 0) |
+ (clearParams.clearStencil ? D3D11_CLEAR_STENCIL : 0);
+ const FLOAT depthClear = gl::clamp01(clearParams.depthValue);
+ const UINT8 stencilClear = clearParams.stencilValue & 0xFF;
- UINT clearFlags = (clearParams.clearDepth ? D3D11_CLEAR_DEPTH : 0) |
- (clearParams.clearStencil ? D3D11_CLEAR_STENCIL : 0);
- FLOAT depthClear = gl::clamp01(clearParams.depthClearValue);
- UINT8 stencilClear = clearParams.stencilClearValue & 0xFF;
+ deviceContext->ClearDepthStencilView(dsv, clearFlags, depthClear, stencilClear);
- deviceContext->ClearDepthStencilView(framebufferDSV, clearFlags, depthClear, stencilClear);
+ dsv = nullptr;
}
}
- if (maskedClearRenderTargets.size() > 0 || maskedClearDepthStencil)
+ if (numRtvs == 0 && dsv == nullptr)
{
- // To clear the render targets and depth stencil in one pass:
- //
- // Render a quad clipped to the scissor rectangle which draws the clear color and a blend
- // state that will perform the required color masking.
- //
- // The quad's depth is equal to the depth clear value with a depth stencil state that
- // will enable or disable depth test/writes if the depth buffer should be cleared or not.
- //
- // The rasterizer state's stencil is set to always pass or fail based on if the stencil
- // should be cleared or not with a stencil write mask of the stencil clear value.
- //
- // ======================================================================================
- //
- // Luckily, the gl spec (ES 3.0.2 pg 183) states that the results of clearing a render-
- // buffer that is not normalized fixed point or floating point with floating point values
- // are undefined so we can just write floats to them and D3D11 will bit cast them to
- // integers.
- //
- // Also, we don't have to worry about attempting to clear a normalized fixed/floating point
- // buffer with integer values because there is no gl API call which would allow it,
- // glClearBuffer* calls only clear a single renderbuffer at a time which is verified to
- // be a compatible clear type.
-
- // Bind all the render targets which need clearing
- ASSERT(maskedClearRenderTargets.size() <= mRenderer->getRendererCaps().maxDrawBuffers);
- std::vector<ID3D11RenderTargetView*> rtvs(maskedClearRenderTargets.size());
- for (unsigned int i = 0; i < maskedClearRenderTargets.size(); i++)
- {
- RenderTarget11 *renderTarget = maskedClearRenderTargets[i].renderTarget;
- ID3D11RenderTargetView *rtv = renderTarget->getRenderTargetView();
- if (!rtv)
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Internal render target view pointer unexpectedly null.");
- }
+ return gl::NoError();
+ }
- rtvs[i] = rtv;
- }
- ID3D11DepthStencilView *dsv = maskedClearDepthStencil ? maskedClearDepthStencil->getDepthStencilView() : nullptr;
+ // Clear the remaining render targets and depth stencil in one pass by rendering a quad:
+ //
+ // IA/VS: Vertices containing position and color members are passed through to the next stage.
+ // The vertex position has XY coordinates equal to clip extents and a Z component equal to the
+ // Z clear value. The vertex color contains the clear color.
+ //
+ // Rasterizer: Viewport scales the VS output over the entire surface and depending on whether
+ // or not scissoring is enabled the appropriate scissor rect and rasterizerState with or without
+ // the scissor test enabled is set as well.
+ //
+ // DepthStencilTest: DepthTesting, DepthWrites, StencilMask and StencilWrites will be enabled or
+ // disabled or set depending on what the input depthStencil clear parameters are. Since the PS
+ // is not writing out depth or rejecting pixels, this should happen prior to the PS stage.
+ //
+ // PS: Will write out the color values passed through from the previous stage to all outputs.
+ //
+ // OM: BlendState will perform the required color masking and output to RTV(s).
+
+ //
+ // ======================================================================================
+ //
+ // Luckily, the gl spec (ES 3.0.2 pg 183) states that the results of clearing a render-
+ // buffer that is not normalized fixed point or floating point with floating point values
+ // are undefined so we can just write floats to them and D3D11 will bit cast them to
+ // integers.
+ //
+ // Also, we don't have to worry about attempting to clear a normalized fixed/floating point
+ // buffer with integer values because there is no gl API call which would allow it,
+ // glClearBuffer* calls only clear a single renderbuffer at a time which is verified to
+ // be a compatible clear type.
- ID3D11BlendState *blendState = getBlendState(maskedClearRenderTargets);
- const FLOAT blendFactors[4] = { 1.0f, 1.0f, 1.0f, 1.0f };
- const UINT sampleMask = 0xFFFFFFFF;
+ ASSERT(numRtvs <= mRenderer->getNativeCaps().maxDrawBuffers);
- ID3D11DepthStencilState *dsState = getDepthStencilState(clearParams);
- const UINT stencilClear = clearParams.stencilClearValue & 0xFF;
+ // Setup BlendStateKey parameters
+ mBlendStateKey.blendState.colorMaskRed = clearParams.colorMaskRed;
+ mBlendStateKey.blendState.colorMaskGreen = clearParams.colorMaskGreen;
+ mBlendStateKey.blendState.colorMaskBlue = clearParams.colorMaskBlue;
+ mBlendStateKey.blendState.colorMaskAlpha = clearParams.colorMaskAlpha;
+ mBlendStateKey.rtvMax = numRtvs;
+ memcpy(mBlendStateKey.rtvMasks, &rtvMasks[0], sizeof(mBlendStateKey.rtvMasks));
- // Set the vertices
- UINT vertexStride = 0;
- const UINT startIdx = 0;
- ClearShader *shader = nullptr;
- D3D11_MAPPED_SUBRESOURCE mappedResource;
- HRESULT result = deviceContext->Map(mVertexBuffer, 0, D3D11_MAP_WRITE_DISCARD, 0, &mappedResource);
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to map internal masked clear vertex buffer, HRESULT: 0x%X.", result);
- }
+ // Get BlendState
+ const d3d11::BlendState *blendState = nullptr;
+ ANGLE_TRY(mRenderer->getBlendState(mBlendStateKey, &blendState));
- const gl::Rectangle *scissorPtr = clearParams.scissorEnabled ? &clearParams.scissor : nullptr;
- switch (clearParams.colorClearType)
- {
- case GL_FLOAT:
- ApplyVertices(framebufferSize, scissorPtr, clearParams.colorFClearValue, clearParams.depthClearValue, mappedResource.pData);
- vertexStride = sizeof(d3d11::PositionDepthColorVertex<float>);
- shader = mFloatClearShader;
- break;
+ const d3d11::DepthStencilState *dsState = nullptr;
+ const float *zValue = nullptr;
- case GL_UNSIGNED_INT:
- ApplyVertices(framebufferSize, scissorPtr, clearParams.colorUIClearValue, clearParams.depthClearValue, mappedResource.pData);
- vertexStride = sizeof(d3d11::PositionDepthColorVertex<unsigned int>);
- shader = mUintClearShader;
- break;
+ if (dsv)
+ {
+ // Setup DepthStencilStateKey
+ mDepthStencilStateKey.depthTest = clearParams.clearDepth;
+ mDepthStencilStateKey.depthMask = clearParams.clearDepth;
+ mDepthStencilStateKey.stencilWritemask = clearParams.stencilWriteMask;
+ mDepthStencilStateKey.stencilTest = clearParams.clearStencil;
+
+ // Get DepthStencilState
+ ANGLE_TRY(mRenderer->getDepthStencilState(mDepthStencilStateKey, &dsState));
+ zValue = clearParams.clearDepth ? &clearParams.depthValue : nullptr;
+ }
- case GL_INT:
- ApplyVertices(framebufferSize, scissorPtr, clearParams.colorIClearValue, clearParams.depthClearValue, mappedResource.pData);
- vertexStride = sizeof(d3d11::PositionDepthColorVertex<int>);
- shader = mIntClearShader;
- break;
+ bool dirtyCb = false;
- default:
+ // Compare the input color/z values against the CB cache and update it if necessary
+ switch (clearParams.colorType)
+ {
+ case GL_FLOAT:
+ dirtyCb = UpdateDataCache(reinterpret_cast<RtvDsvClearInfo<float> *>(&mShaderData),
+ clearParams.colorF, zValue, numRtvs, colorMask);
+ break;
+ case GL_UNSIGNED_INT:
+ dirtyCb = UpdateDataCache(reinterpret_cast<RtvDsvClearInfo<uint32_t> *>(&mShaderData),
+ clearParams.colorUI, zValue, numRtvs, colorMask);
+ break;
+ case GL_INT:
+ dirtyCb = UpdateDataCache(reinterpret_cast<RtvDsvClearInfo<int> *>(&mShaderData),
+ clearParams.colorI, zValue, numRtvs, colorMask);
+ break;
+ default:
UNREACHABLE();
break;
- }
-
- deviceContext->Unmap(mVertexBuffer, 0);
-
- // Set the viewport to be the same size as the framebuffer
- D3D11_VIEWPORT viewport;
- viewport.TopLeftX = 0;
- viewport.TopLeftY = 0;
- viewport.Width = static_cast<FLOAT>(framebufferSize.width);
- viewport.Height = static_cast<FLOAT>(framebufferSize.height);
- viewport.MinDepth = 0;
- viewport.MaxDepth = 1;
- deviceContext->RSSetViewports(1, &viewport);
-
- // Apply state
- deviceContext->OMSetBlendState(blendState, blendFactors, sampleMask);
- deviceContext->OMSetDepthStencilState(dsState, stencilClear);
- deviceContext->RSSetState(mRasterizerState);
-
- // Apply shaders
- deviceContext->IASetInputLayout(shader->inputLayout->resolve(device));
- deviceContext->VSSetShader(shader->vertexShader.resolve(device), nullptr, 0);
- deviceContext->PSSetShader(shader->pixelShader.resolve(device), nullptr, 0);
- deviceContext->GSSetShader(nullptr, nullptr, 0);
-
- // Apply vertex buffer
- deviceContext->IASetVertexBuffers(0, 1, &mVertexBuffer, &vertexStride, &startIdx);
- deviceContext->IASetPrimitiveTopology(D3D_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP);
-
- // Apply render targets
- deviceContext->OMSetRenderTargets(static_cast<unsigned int>(rtvs.size()),
- (rtvs.empty() ? nullptr : &rtvs[0]), dsv);
-
- // Draw the clear quad
- deviceContext->Draw(4, 0);
-
- // Clean up
- mRenderer->markAllStateDirty();
}
- return gl::Error(GL_NO_ERROR);
-}
+ ANGLE_TRY(ensureConstantBufferCreated());
-ID3D11BlendState *Clear11::getBlendState(const std::vector<MaskedRenderTarget>& rts)
-{
- ClearBlendInfo blendKey = {};
- for (unsigned int i = 0; i < D3D11_SIMULTANEOUS_RENDER_TARGET_COUNT; i++)
+ if (dirtyCb)
{
- if (i < rts.size())
- {
- RenderTarget11 *rt = rts[i].renderTarget;
- const gl::InternalFormat &formatInfo = gl::GetInternalFormatInfo(rt->getInternalFormat());
-
- blendKey.maskChannels[i][0] = (rts[i].colorMask[0] && formatInfo.redBits > 0);
- blendKey.maskChannels[i][1] = (rts[i].colorMask[1] && formatInfo.greenBits > 0);
- blendKey.maskChannels[i][2] = (rts[i].colorMask[2] && formatInfo.blueBits > 0);
- blendKey.maskChannels[i][3] = (rts[i].colorMask[3] && formatInfo.alphaBits > 0);
- }
- else
+ // Update the constant buffer with the updated cache contents
+ // TODO(Shahmeer): Consider using UpdateSubresource1 D3D11_COPY_DISCARD where possible.
+ D3D11_MAPPED_SUBRESOURCE mappedResource;
+ HRESULT result = deviceContext->Map(mConstantBuffer.get(), 0, D3D11_MAP_WRITE_DISCARD, 0,
+ &mappedResource);
+ if (FAILED(result))
{
- blendKey.maskChannels[i][0] = false;
- blendKey.maskChannels[i][1] = false;
- blendKey.maskChannels[i][2] = false;
- blendKey.maskChannels[i][3] = false;
+ return gl::OutOfMemory() << "Clear11: Failed to map CB, " << gl::FmtHR(result);
}
- }
- ClearBlendStateMap::const_iterator i = mClearBlendStates.find(blendKey);
- if (i != mClearBlendStates.end())
- {
- return i->second;
+ memcpy(mappedResource.pData, &mShaderData, g_ConstantBufferSize);
+ deviceContext->Unmap(mConstantBuffer.get(), 0);
}
- else
- {
- D3D11_BLEND_DESC blendDesc = { 0 };
- blendDesc.AlphaToCoverageEnable = FALSE;
- blendDesc.IndependentBlendEnable = (rts.size() > 1) ? TRUE : FALSE;
- for (unsigned int j = 0; j < D3D11_SIMULTANEOUS_RENDER_TARGET_COUNT; j++)
- {
- blendDesc.RenderTarget[j].BlendEnable = FALSE;
- blendDesc.RenderTarget[j].RenderTargetWriteMask = gl_d3d11::ConvertColorMask(blendKey.maskChannels[j][0],
- blendKey.maskChannels[j][1],
- blendKey.maskChannels[j][2],
- blendKey.maskChannels[j][3]);
- }
+ auto *stateManager = mRenderer->getStateManager();
- ID3D11Device *device = mRenderer->getDevice();
- ID3D11BlendState* blendState = nullptr;
- HRESULT result = device->CreateBlendState(&blendDesc, &blendState);
- if (FAILED(result) || !blendState)
- {
- ERR("Unable to create a ID3D11BlendState, HRESULT: 0x%X.", result);
- return nullptr;
- }
+ // Set the viewport to be the same size as the framebuffer.
+ stateManager->setSimpleViewport(framebufferSize);
- mClearBlendStates[blendKey] = blendState;
+ // Apply state
+ stateManager->setSimpleBlendState(blendState);
- return blendState;
- }
-}
+ const UINT stencilValue = clearParams.stencilValue & 0xFF;
+ stateManager->setDepthStencilState(dsState, stencilValue);
-ID3D11DepthStencilState *Clear11::getDepthStencilState(const ClearParameters &clearParams)
-{
- ClearDepthStencilInfo dsKey = { 0 };
- dsKey.clearDepth = clearParams.clearDepth;
- dsKey.clearStencil = clearParams.clearStencil;
- dsKey.stencilWriteMask = clearParams.stencilWriteMask & 0xFF;
+ if (needScissoredClear)
+ {
+ stateManager->setRasterizerState(&mScissorEnabledRasterizerState);
+ }
+ else
+ {
+ stateManager->setRasterizerState(&mScissorDisabledRasterizerState);
+ }
- ClearDepthStencilStateMap::const_iterator i = mClearDepthStencilStates.find(dsKey);
- if (i != mClearDepthStencilStates.end())
+ // Get Shaders
+ const d3d11::VertexShader *vs = nullptr;
+ const d3d11::GeometryShader *gs = nullptr;
+ const d3d11::InputLayout *il = nullptr;
+ const d3d11::PixelShader *ps = nullptr;
+ const bool hasLayeredLayout =
+ (fboData.getMultiviewLayout() == GL_FRAMEBUFFER_MULTIVIEW_LAYERED_ANGLE);
+ ANGLE_TRY(mShaderManager.getShadersAndLayout(mRenderer, clearParams.colorType, numRtvs,
+ hasLayeredLayout, &il, &vs, &gs, &ps));
+
+ // Apply Shaders
+ stateManager->setDrawShaders(vs, gs, ps);
+ stateManager->setPixelConstantBuffer(0, &mConstantBuffer);
+
+ // Bind IL & VB if needed
+ stateManager->setIndexBuffer(nullptr, DXGI_FORMAT_UNKNOWN, 0);
+ stateManager->setInputLayout(il);
+
+ if (useVertexBuffer())
{
- return i->second;
+ ANGLE_TRY(ensureVertexBufferCreated());
+ stateManager->setSingleVertexBuffer(&mVertexBuffer, g_VertexSize, 0);
}
else
{
- D3D11_DEPTH_STENCIL_DESC dsDesc = { 0 };
- dsDesc.DepthEnable = dsKey.clearDepth ? TRUE : FALSE;
- dsDesc.DepthWriteMask = dsKey.clearDepth ? D3D11_DEPTH_WRITE_MASK_ALL : D3D11_DEPTH_WRITE_MASK_ZERO;
- dsDesc.DepthFunc = D3D11_COMPARISON_ALWAYS;
- dsDesc.StencilEnable = dsKey.clearStencil ? TRUE : FALSE;
- dsDesc.StencilReadMask = 0;
- dsDesc.StencilWriteMask = dsKey.stencilWriteMask;
- dsDesc.FrontFace.StencilFailOp = D3D11_STENCIL_OP_REPLACE;
- dsDesc.FrontFace.StencilDepthFailOp = D3D11_STENCIL_OP_REPLACE;
- dsDesc.FrontFace.StencilPassOp = D3D11_STENCIL_OP_REPLACE;
- dsDesc.FrontFace.StencilFunc = D3D11_COMPARISON_ALWAYS;
- dsDesc.BackFace.StencilFailOp = D3D11_STENCIL_OP_REPLACE;
- dsDesc.BackFace.StencilDepthFailOp = D3D11_STENCIL_OP_REPLACE;
- dsDesc.BackFace.StencilPassOp = D3D11_STENCIL_OP_REPLACE;
- dsDesc.BackFace.StencilFunc = D3D11_COMPARISON_ALWAYS;
-
- ID3D11Device *device = mRenderer->getDevice();
- ID3D11DepthStencilState* dsState = nullptr;
- HRESULT result = device->CreateDepthStencilState(&dsDesc, &dsState);
- if (FAILED(result) || !dsState)
- {
- ERR("Unable to create a ID3D11DepthStencilState, HRESULT: 0x%X.", result);
- return nullptr;
- }
+ stateManager->setSingleVertexBuffer(nullptr, 0, 0);
+ }
- mClearDepthStencilStates[dsKey] = dsState;
+ stateManager->setPrimitiveTopology(D3D_PRIMITIVE_TOPOLOGY_TRIANGLELIST);
- return dsState;
+ // Apply render targets
+ stateManager->setRenderTargets(&rtvs[0], numRtvs, dsv);
+
+ // If scissors are necessary to be applied, then the number of clears is the number of scissor
+ // rects. If no scissors are necessary, then a single full-size clear is enough.
+ size_t necessaryNumClears = needScissoredClear ? scissorRects.size() : 1u;
+ for (size_t i = 0u; i < necessaryNumClears; ++i)
+ {
+ if (needScissoredClear)
+ {
+ ASSERT(i < scissorRects.size());
+ stateManager->setScissorRectD3D(scissorRects[i]);
+ }
+ // Draw the fullscreen quad.
+ if (!hasLayeredLayout || isSideBySideFBO)
+ {
+ deviceContext->Draw(6, 0);
+ }
+ else
+ {
+ ASSERT(hasLayeredLayout);
+ deviceContext->DrawInstanced(6, static_cast<UINT>(fboData.getNumViews()), 0, 0);
+ }
}
-}
+ return gl::NoError();
}
+
+} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Clear11.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Clear11.h
index 3ff73c85d1..a09812c42b 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Clear11.h
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Clear11.h
@@ -23,6 +23,14 @@ class Renderer11;
class RenderTarget11;
struct ClearParameters;
+template <typename T>
+struct RtvDsvClearInfo
+{
+ T r, g, b, a;
+ float z;
+ float c1padding[3];
+};
+
class Clear11 : angle::NonCopyable
{
public:
@@ -30,68 +38,63 @@ class Clear11 : angle::NonCopyable
~Clear11();
// Clears the framebuffer with the supplied clear parameters, assumes that the framebuffer is currently applied.
- gl::Error clearFramebuffer(const ClearParameters &clearParams, const gl::Framebuffer::Data &fboData);
+ gl::Error clearFramebuffer(const gl::Context *context,
+ const ClearParameters &clearParams,
+ const gl::FramebufferState &fboData);
private:
- struct MaskedRenderTarget
- {
- bool colorMask[4];
- RenderTarget11 *renderTarget;
- };
-
- ID3D11BlendState *getBlendState(const std::vector<MaskedRenderTarget> &rts);
- ID3D11DepthStencilState *getDepthStencilState(const ClearParameters &clearParams);
-
- struct ClearShader final : public angle::NonCopyable
+ class ShaderManager final : angle::NonCopyable
{
- ClearShader(DXGI_FORMAT colorType,
- const char *inputLayoutName,
- const BYTE *vsByteCode,
- size_t vsSize,
- const char *vsDebugName,
- const BYTE *psByteCode,
- size_t psSize,
- const char *psDebugName);
- ~ClearShader();
-
- d3d11::LazyInputLayout *inputLayout;
- d3d11::LazyShader<ID3D11VertexShader> vertexShader;
- d3d11::LazyShader<ID3D11PixelShader> pixelShader;
+ public:
+ ShaderManager();
+ ~ShaderManager();
+ gl::Error getShadersAndLayout(Renderer11 *renderer,
+ const INT clearType,
+ const uint32_t numRTs,
+ const bool hasLayeredLayout,
+ const d3d11::InputLayout **il,
+ const d3d11::VertexShader **vs,
+ const d3d11::GeometryShader **gs,
+ const d3d11::PixelShader **ps);
+
+ private:
+ constexpr static size_t kNumShaders = D3D11_SIMULTANEOUS_RENDER_TARGET_COUNT;
+
+ d3d11::InputLayout mIl9;
+ d3d11::LazyShader<ID3D11VertexShader> mVs9;
+ d3d11::LazyShader<ID3D11PixelShader> mPsFloat9;
+ d3d11::LazyShader<ID3D11VertexShader> mVs;
+ d3d11::LazyShader<ID3D11VertexShader> mVsMultiview;
+ d3d11::LazyShader<ID3D11GeometryShader> mGsMultiview;
+ d3d11::LazyShader<ID3D11PixelShader> mPsDepth;
+ std::array<d3d11::LazyShader<ID3D11PixelShader>, kNumShaders> mPsFloat;
+ std::array<d3d11::LazyShader<ID3D11PixelShader>, kNumShaders> mPsUInt;
+ std::array<d3d11::LazyShader<ID3D11PixelShader>, kNumShaders> mPsSInt;
};
- template <unsigned int vsSize, unsigned int psSize>
- static ClearShader CreateClearShader(ID3D11Device *device, DXGI_FORMAT colorType, const BYTE(&vsByteCode)[vsSize], const BYTE(&psByteCode)[psSize]);
-
- struct ClearBlendInfo
- {
- bool maskChannels[D3D11_SIMULTANEOUS_RENDER_TARGET_COUNT][4];
- };
- typedef bool(*ClearBlendInfoComparisonFunction)(const ClearBlendInfo&, const ClearBlendInfo &);
- typedef std::map<ClearBlendInfo, ID3D11BlendState*, ClearBlendInfoComparisonFunction> ClearBlendStateMap;
-
- struct ClearDepthStencilInfo
- {
- bool clearDepth;
- bool clearStencil;
- UINT8 stencilWriteMask;
- };
- typedef bool(*ClearDepthStencilInfoComparisonFunction)(const ClearDepthStencilInfo&, const ClearDepthStencilInfo &);
- typedef std::map<ClearDepthStencilInfo, ID3D11DepthStencilState*, ClearDepthStencilInfoComparisonFunction> ClearDepthStencilStateMap;
+ bool useVertexBuffer() const;
+ gl::Error ensureConstantBufferCreated();
+ gl::Error ensureVertexBufferCreated();
+ gl::Error ensureResourcesInitialized();
Renderer11 *mRenderer;
+ bool mResourcesInitialized;
- ClearBlendStateMap mClearBlendStates;
-
- ClearShader *mFloatClearShader;
- ClearShader *mUintClearShader;
- ClearShader *mIntClearShader;
+ // States
+ d3d11::RasterizerState mScissorEnabledRasterizerState;
+ d3d11::RasterizerState mScissorDisabledRasterizerState;
+ gl::DepthStencilState mDepthStencilStateKey;
+ d3d11::BlendStateKey mBlendStateKey;
- ClearDepthStencilStateMap mClearDepthStencilStates;
+ // Shaders and shader resources
+ ShaderManager mShaderManager;
+ d3d11::Buffer mConstantBuffer;
+ d3d11::Buffer mVertexBuffer;
- ID3D11Buffer *mVertexBuffer;
- ID3D11RasterizerState *mRasterizerState;
+ // Buffer data and draw parameters
+ RtvDsvClearInfo<float> mShaderData;
};
-}
+} // namespace rx
#endif // LIBANGLE_RENDERER_D3D_D3D11_CLEAR11_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Context11.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Context11.cpp
new file mode 100644
index 0000000000..b79dd3603a
--- /dev/null
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Context11.cpp
@@ -0,0 +1,405 @@
+//
+// Copyright 2016 The ANGLE Project Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+//
+// Context11:
+// D3D11-specific functionality associated with a GL Context.
+//
+
+#include "libANGLE/renderer/d3d/d3d11/Context11.h"
+
+#include "common/string_utils.h"
+#include "libANGLE/Context.h"
+#include "libANGLE/MemoryProgramCache.h"
+#include "libANGLE/renderer/d3d/CompilerD3D.h"
+#include "libANGLE/renderer/d3d/ProgramD3D.h"
+#include "libANGLE/renderer/d3d/RenderbufferD3D.h"
+#include "libANGLE/renderer/d3d/SamplerD3D.h"
+#include "libANGLE/renderer/d3d/ShaderD3D.h"
+#include "libANGLE/renderer/d3d/TextureD3D.h"
+#include "libANGLE/renderer/d3d/d3d11/Buffer11.h"
+#include "libANGLE/renderer/d3d/d3d11/Fence11.h"
+#include "libANGLE/renderer/d3d/d3d11/Framebuffer11.h"
+#include "libANGLE/renderer/d3d/d3d11/ProgramPipeline11.h"
+#include "libANGLE/renderer/d3d/d3d11/Renderer11.h"
+#include "libANGLE/renderer/d3d/d3d11/StateManager11.h"
+#include "libANGLE/renderer/d3d/d3d11/TransformFeedback11.h"
+#include "libANGLE/renderer/d3d/d3d11/VertexArray11.h"
+
+namespace rx
+{
+
+Context11::Context11(const gl::ContextState &state, Renderer11 *renderer)
+ : ContextImpl(state), mRenderer(renderer)
+{
+}
+
+Context11::~Context11()
+{
+}
+
+gl::Error Context11::initialize()
+{
+ return gl::NoError();
+}
+
+CompilerImpl *Context11::createCompiler()
+{
+ if (mRenderer->getRenderer11DeviceCaps().featureLevel <= D3D_FEATURE_LEVEL_9_3)
+ {
+ return new CompilerD3D(SH_HLSL_4_0_FL9_3_OUTPUT);
+ }
+ else
+ {
+ return new CompilerD3D(SH_HLSL_4_1_OUTPUT);
+ }
+}
+
+ShaderImpl *Context11::createShader(const gl::ShaderState &data)
+{
+ return new ShaderD3D(data, mRenderer->getWorkarounds(), mRenderer->getNativeExtensions());
+}
+
+ProgramImpl *Context11::createProgram(const gl::ProgramState &data)
+{
+ return new ProgramD3D(data, mRenderer);
+}
+
+FramebufferImpl *Context11::createFramebuffer(const gl::FramebufferState &data)
+{
+ return new Framebuffer11(data, mRenderer);
+}
+
+TextureImpl *Context11::createTexture(const gl::TextureState &state)
+{
+ switch (state.getTarget())
+ {
+ case GL_TEXTURE_2D:
+ return new TextureD3D_2D(state, mRenderer);
+ case GL_TEXTURE_CUBE_MAP:
+ return new TextureD3D_Cube(state, mRenderer);
+ case GL_TEXTURE_3D:
+ return new TextureD3D_3D(state, mRenderer);
+ case GL_TEXTURE_2D_ARRAY:
+ return new TextureD3D_2DArray(state, mRenderer);
+ case GL_TEXTURE_EXTERNAL_OES:
+ return new TextureD3D_External(state, mRenderer);
+ case GL_TEXTURE_2D_MULTISAMPLE:
+ return new TextureD3D_2DMultisample(state, mRenderer);
+ break;
+ default:
+ UNREACHABLE();
+ }
+
+ return nullptr;
+}
+
+RenderbufferImpl *Context11::createRenderbuffer()
+{
+ return new RenderbufferD3D(mRenderer);
+}
+
+BufferImpl *Context11::createBuffer(const gl::BufferState &state)
+{
+ Buffer11 *buffer = new Buffer11(state, mRenderer);
+ mRenderer->onBufferCreate(buffer);
+ return buffer;
+}
+
+VertexArrayImpl *Context11::createVertexArray(const gl::VertexArrayState &data)
+{
+ return new VertexArray11(data);
+}
+
+QueryImpl *Context11::createQuery(GLenum type)
+{
+ return new Query11(mRenderer, type);
+}
+
+FenceNVImpl *Context11::createFenceNV()
+{
+ return new FenceNV11(mRenderer);
+}
+
+SyncImpl *Context11::createSync()
+{
+ return new Sync11(mRenderer);
+}
+
+TransformFeedbackImpl *Context11::createTransformFeedback(const gl::TransformFeedbackState &state)
+{
+ return new TransformFeedback11(state, mRenderer);
+}
+
+SamplerImpl *Context11::createSampler(const gl::SamplerState &state)
+{
+ return new SamplerD3D(state);
+}
+
+ProgramPipelineImpl *Context11::createProgramPipeline(const gl::ProgramPipelineState &data)
+{
+ return new ProgramPipeline11(data);
+}
+
+std::vector<PathImpl *> Context11::createPaths(GLsizei)
+{
+ return std::vector<PathImpl *>();
+}
+
+gl::Error Context11::flush(const gl::Context *context)
+{
+ return mRenderer->flush();
+}
+
+gl::Error Context11::finish(const gl::Context *context)
+{
+ return mRenderer->finish();
+}
+
+gl::Error Context11::drawArrays(const gl::Context *context, GLenum mode, GLint first, GLsizei count)
+{
+ ANGLE_TRY(prepareForDrawCall(context, mode));
+ return mRenderer->drawArrays(context, mode, first, count, 0);
+}
+
+gl::Error Context11::drawArraysInstanced(const gl::Context *context,
+ GLenum mode,
+ GLint first,
+ GLsizei count,
+ GLsizei instanceCount)
+{
+ ANGLE_TRY(prepareForDrawCall(context, mode));
+ return mRenderer->drawArrays(context, mode, first, count, instanceCount);
+}
+
+gl::Error Context11::drawElements(const gl::Context *context,
+ GLenum mode,
+ GLsizei count,
+ GLenum type,
+ const void *indices)
+{
+ ANGLE_TRY(prepareForDrawCall(context, mode));
+ return mRenderer->drawElements(context, mode, count, type, indices, 0);
+}
+
+gl::Error Context11::drawElementsInstanced(const gl::Context *context,
+ GLenum mode,
+ GLsizei count,
+ GLenum type,
+ const void *indices,
+ GLsizei instances)
+{
+ ANGLE_TRY(prepareForDrawCall(context, mode));
+ return mRenderer->drawElements(context, mode, count, type, indices, instances);
+}
+
+gl::Error Context11::drawRangeElements(const gl::Context *context,
+ GLenum mode,
+ GLuint start,
+ GLuint end,
+ GLsizei count,
+ GLenum type,
+ const void *indices)
+{
+ ANGLE_TRY(prepareForDrawCall(context, mode));
+ return mRenderer->drawElements(context, mode, count, type, indices, 0);
+}
+
+gl::Error Context11::drawArraysIndirect(const gl::Context *context,
+ GLenum mode,
+ const void *indirect)
+{
+ ANGLE_TRY(prepareForDrawCall(context, mode));
+ return mRenderer->drawArraysIndirect(context, mode, indirect);
+}
+
+gl::Error Context11::drawElementsIndirect(const gl::Context *context,
+ GLenum mode,
+ GLenum type,
+ const void *indirect)
+{
+ ANGLE_TRY(prepareForDrawCall(context, mode));
+ return mRenderer->drawElementsIndirect(context, mode, type, indirect);
+}
+
+GLenum Context11::getResetStatus()
+{
+ return mRenderer->getResetStatus();
+}
+
+std::string Context11::getVendorString() const
+{
+ return mRenderer->getVendorString();
+}
+
+std::string Context11::getRendererDescription() const
+{
+ return mRenderer->getRendererDescription();
+}
+
+void Context11::insertEventMarker(GLsizei length, const char *marker)
+{
+ auto optionalString = angle::WidenString(static_cast<size_t>(length), marker);
+ if (optionalString.valid())
+ {
+ mRenderer->getAnnotator()->setMarker(optionalString.value().data());
+ }
+}
+
+void Context11::pushGroupMarker(GLsizei length, const char *marker)
+{
+ auto optionalString = angle::WidenString(static_cast<size_t>(length), marker);
+ if (optionalString.valid())
+ {
+ mRenderer->getAnnotator()->beginEvent(optionalString.value().data());
+ }
+}
+
+void Context11::popGroupMarker()
+{
+ mRenderer->getAnnotator()->endEvent();
+}
+
+void Context11::pushDebugGroup(GLenum source, GLuint id, GLsizei length, const char *message)
+{
+ // Fall through to the EXT_debug_marker functions
+ pushGroupMarker(length, message);
+}
+
+void Context11::popDebugGroup()
+{
+ // Fall through to the EXT_debug_marker functions
+ popGroupMarker();
+}
+
+void Context11::syncState(const gl::Context *context, const gl::State::DirtyBits &dirtyBits)
+{
+ mRenderer->getStateManager()->syncState(context, dirtyBits);
+}
+
+GLint Context11::getGPUDisjoint()
+{
+ return mRenderer->getGPUDisjoint();
+}
+
+GLint64 Context11::getTimestamp()
+{
+ return mRenderer->getTimestamp();
+}
+
+void Context11::onMakeCurrent(const gl::Context *context)
+{
+ ANGLE_SWALLOW_ERR(mRenderer->getStateManager()->onMakeCurrent(context));
+}
+
+const gl::Caps &Context11::getNativeCaps() const
+{
+ return mRenderer->getNativeCaps();
+}
+
+const gl::TextureCapsMap &Context11::getNativeTextureCaps() const
+{
+ return mRenderer->getNativeTextureCaps();
+}
+
+const gl::Extensions &Context11::getNativeExtensions() const
+{
+ return mRenderer->getNativeExtensions();
+}
+
+const gl::Limitations &Context11::getNativeLimitations() const
+{
+ return mRenderer->getNativeLimitations();
+}
+
+gl::Error Context11::dispatchCompute(const gl::Context *context,
+ GLuint numGroupsX,
+ GLuint numGroupsY,
+ GLuint numGroupsZ)
+{
+ return mRenderer->dispatchCompute(context, numGroupsX, numGroupsY, numGroupsZ);
+}
+
+gl::Error Context11::triggerDrawCallProgramRecompilation(const gl::Context *context,
+ GLenum drawMode)
+{
+ const auto &glState = context->getGLState();
+ const auto *va11 = GetImplAs<VertexArray11>(glState.getVertexArray());
+ const auto *drawFBO = glState.getDrawFramebuffer();
+ gl::Program *program = glState.getProgram();
+ ProgramD3D *programD3D = GetImplAs<ProgramD3D>(program);
+
+ programD3D->updateCachedInputLayout(va11->getCurrentStateSerial(), glState);
+ programD3D->updateCachedOutputLayout(context, drawFBO);
+
+ bool recompileVS = !programD3D->hasVertexExecutableForCachedInputLayout();
+ bool recompileGS = !programD3D->hasGeometryExecutableForPrimitiveType(drawMode);
+ bool recompilePS = !programD3D->hasPixelExecutableForCachedOutputLayout();
+
+ if (!recompileVS && !recompileGS && !recompilePS)
+ {
+ return gl::NoError();
+ }
+
+ // Load the compiler if necessary and recompile the programs.
+ ANGLE_TRY(mRenderer->ensureHLSLCompilerInitialized());
+
+ gl::InfoLog infoLog;
+
+ if (recompileVS)
+ {
+ ShaderExecutableD3D *vertexExe = nullptr;
+ ANGLE_TRY(programD3D->getVertexExecutableForCachedInputLayout(&vertexExe, &infoLog));
+ if (!programD3D->hasVertexExecutableForCachedInputLayout())
+ {
+ ASSERT(infoLog.getLength() > 0);
+ ERR() << "Dynamic recompilation error log: " << infoLog.str();
+ return gl::InternalError()
+ << "Error compiling dynamic vertex executable:" << infoLog.str();
+ }
+ }
+
+ if (recompileGS)
+ {
+ ShaderExecutableD3D *geometryExe = nullptr;
+ ANGLE_TRY(programD3D->getGeometryExecutableForPrimitiveType(context, drawMode, &geometryExe,
+ &infoLog));
+ if (!programD3D->hasGeometryExecutableForPrimitiveType(drawMode))
+ {
+ ASSERT(infoLog.getLength() > 0);
+ ERR() << "Dynamic recompilation error log: " << infoLog.str();
+ return gl::InternalError()
+ << "Error compiling dynamic geometry executable:" << infoLog.str();
+ }
+ }
+
+ if (recompilePS)
+ {
+ ShaderExecutableD3D *pixelExe = nullptr;
+ ANGLE_TRY(programD3D->getPixelExecutableForCachedOutputLayout(&pixelExe, &infoLog));
+ if (!programD3D->hasPixelExecutableForCachedOutputLayout())
+ {
+ ASSERT(infoLog.getLength() > 0);
+ ERR() << "Dynamic recompilation error log: " << infoLog.str();
+ return gl::InternalError()
+ << "Error compiling dynamic pixel executable:" << infoLog.str();
+ }
+ }
+
+ // Refresh the program cache entry.
+ if (mMemoryProgramCache)
+ {
+ mMemoryProgramCache->updateProgram(context, program);
+ }
+
+ return gl::NoError();
+}
+
+gl::Error Context11::prepareForDrawCall(const gl::Context *context, GLenum drawMode)
+{
+ ANGLE_TRY(mRenderer->getStateManager()->updateState(context, drawMode));
+ return gl::NoError();
+}
+
+} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Context11.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Context11.h
new file mode 100644
index 0000000000..dd99111b19
--- /dev/null
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Context11.h
@@ -0,0 +1,155 @@
+//
+// Copyright 2016 The ANGLE Project Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+//
+// Context11:
+// D3D11-specific functionality associated with a GL Context.
+//
+
+#ifndef LIBANGLE_RENDERER_D3D_D3D11_CONTEXT11_H_
+#define LIBANGLE_RENDERER_D3D_D3D11_CONTEXT11_H_
+
+#include "libANGLE/renderer/ContextImpl.h"
+
+namespace rx
+{
+class Renderer11;
+
+class Context11 : public ContextImpl
+{
+ public:
+ Context11(const gl::ContextState &state, Renderer11 *renderer);
+ ~Context11() override;
+
+ gl::Error initialize() override;
+
+ // Shader creation
+ CompilerImpl *createCompiler() override;
+ ShaderImpl *createShader(const gl::ShaderState &data) override;
+ ProgramImpl *createProgram(const gl::ProgramState &data) override;
+
+ // Framebuffer creation
+ FramebufferImpl *createFramebuffer(const gl::FramebufferState &data) override;
+
+ // Texture creation
+ TextureImpl *createTexture(const gl::TextureState &state) override;
+
+ // Renderbuffer creation
+ RenderbufferImpl *createRenderbuffer() override;
+
+ // Buffer creation
+ BufferImpl *createBuffer(const gl::BufferState &state) override;
+
+ // Vertex Array creation
+ VertexArrayImpl *createVertexArray(const gl::VertexArrayState &data) override;
+
+ // Query and Fence creation
+ QueryImpl *createQuery(GLenum type) override;
+ FenceNVImpl *createFenceNV() override;
+ SyncImpl *createSync() override;
+
+ // Transform Feedback creation
+ TransformFeedbackImpl *createTransformFeedback(
+ const gl::TransformFeedbackState &state) override;
+
+ // Sampler object creation
+ SamplerImpl *createSampler(const gl::SamplerState &state) override;
+
+ // Program Pipeline object creation
+ ProgramPipelineImpl *createProgramPipeline(const gl::ProgramPipelineState &data) override;
+
+ // Path object creation.
+ std::vector<PathImpl *> createPaths(GLsizei) override;
+
+ // Flush and finish.
+ gl::Error flush(const gl::Context *context) override;
+ gl::Error finish(const gl::Context *context) override;
+
+ // Drawing methods.
+ gl::Error drawArrays(const gl::Context *context,
+ GLenum mode,
+ GLint first,
+ GLsizei count) override;
+ gl::Error drawArraysInstanced(const gl::Context *context,
+ GLenum mode,
+ GLint first,
+ GLsizei count,
+ GLsizei instanceCount) override;
+
+ gl::Error drawElements(const gl::Context *context,
+ GLenum mode,
+ GLsizei count,
+ GLenum type,
+ const void *indices) override;
+ gl::Error drawElementsInstanced(const gl::Context *context,
+ GLenum mode,
+ GLsizei count,
+ GLenum type,
+ const void *indices,
+ GLsizei instances) override;
+ gl::Error drawRangeElements(const gl::Context *context,
+ GLenum mode,
+ GLuint start,
+ GLuint end,
+ GLsizei count,
+ GLenum type,
+ const void *indices) override;
+ gl::Error drawArraysIndirect(const gl::Context *context,
+ GLenum mode,
+ const void *indirect) override;
+ gl::Error drawElementsIndirect(const gl::Context *context,
+ GLenum mode,
+ GLenum type,
+ const void *indirect) override;
+
+ // Device loss
+ GLenum getResetStatus() override;
+
+ // Vendor and description strings.
+ std::string getVendorString() const override;
+ std::string getRendererDescription() const override;
+
+ // EXT_debug_marker
+ void insertEventMarker(GLsizei length, const char *marker) override;
+ void pushGroupMarker(GLsizei length, const char *marker) override;
+ void popGroupMarker() override;
+
+ // KHR_debug
+ void pushDebugGroup(GLenum source, GLuint id, GLsizei length, const char *message) override;
+ void popDebugGroup() override;
+
+ // State sync with dirty bits.
+ void syncState(const gl::Context *context, const gl::State::DirtyBits &dirtyBits) override;
+
+ // Disjoint timer queries
+ GLint getGPUDisjoint() override;
+ GLint64 getTimestamp() override;
+
+ // Context switching
+ void onMakeCurrent(const gl::Context *context) override;
+
+ // Caps queries
+ const gl::Caps &getNativeCaps() const override;
+ const gl::TextureCapsMap &getNativeTextureCaps() const override;
+ const gl::Extensions &getNativeExtensions() const override;
+ const gl::Limitations &getNativeLimitations() const override;
+
+ Renderer11 *getRenderer() const { return mRenderer; }
+
+ gl::Error dispatchCompute(const gl::Context *context,
+ GLuint numGroupsX,
+ GLuint numGroupsY,
+ GLuint numGroupsZ) override;
+
+ gl::Error triggerDrawCallProgramRecompilation(const gl::Context *context, GLenum drawMode);
+
+ private:
+ gl::Error prepareForDrawCall(const gl::Context *context, GLenum drawMode);
+
+ Renderer11 *mRenderer;
+};
+
+} // namespace rx
+
+#endif // LIBANGLE_RENDERER_D3D_D3D11_CONTEXT11_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/DebugAnnotator11.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/DebugAnnotator11.cpp
index 1c35ab45cc..1e70363e11 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/DebugAnnotator11.cpp
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/DebugAnnotator11.cpp
@@ -27,9 +27,7 @@ DebugAnnotator11::~DebugAnnotator11()
{
if (mInitialized)
{
-#if defined(ANGLE_ENABLE_D3D11_1)
SafeRelease(mUserDefinedAnnotation);
-#endif
#if !defined(ANGLE_ENABLE_WINDOWS_STORE)
FreeLibrary(mD3d11Module);
@@ -43,9 +41,7 @@ void DebugAnnotator11::beginEvent(const wchar_t *eventName)
if (mUserDefinedAnnotation != nullptr)
{
-#if defined(ANGLE_ENABLE_D3D11_1)
mUserDefinedAnnotation->BeginEvent(eventName);
-#endif
}
}
@@ -55,9 +51,7 @@ void DebugAnnotator11::endEvent()
if (mUserDefinedAnnotation != nullptr)
{
-#if defined(ANGLE_ENABLE_D3D11_1)
mUserDefinedAnnotation->EndEvent();
-#endif
}
}
@@ -67,16 +61,14 @@ void DebugAnnotator11::setMarker(const wchar_t *markerName)
if (mUserDefinedAnnotation != nullptr)
{
-#if defined(ANGLE_ENABLE_D3D11_1)
mUserDefinedAnnotation->SetMarker(markerName);
-#endif
}
}
bool DebugAnnotator11::getStatus()
{
#if defined(ANGLE_ENABLE_WINDOWS_STORE)
-#if (NTDDI_VERSION == NTDDI_WIN10)
+ static_assert(NTDDI_VERSION >= NTDDI_WIN10, "GetStatus only works on Win10 and above");
initializeDevice();
if (mUserDefinedAnnotation != nullptr)
@@ -85,38 +77,6 @@ bool DebugAnnotator11::getStatus()
}
return true; // Default if initializeDevice() failed
-#elif defined(_DEBUG) && (WINAPI_FAMILY != WINAPI_FAMILY_PHONE_APP)
- static bool underCapture = true;
-
- // ID3DUserDefinedAnnotation::GetStatus doesn't work with the Graphics Diagnostics tools in
- // Windows 8.1/Visual Studio 2013. We can use IDXGraphicsAnalysis, though.
- // The call to GetDebugInterface1 only succeeds if the app is under capture.
- // This should only be called in DEBUG mode.
- // If an app links against DXGIGetDebugInterface1 in release mode then it will fail Windows
- // Store ingestion checks.
-
- // Cache the result to reduce the number of calls to DXGIGetDebugInterface1
- static bool triedIDXGraphicsAnalysis = false;
-
- if (!triedIDXGraphicsAnalysis)
- {
- IDXGraphicsAnalysis *graphicsAnalysis = nullptr;
-
- HRESULT result = DXGIGetDebugInterface1(0, IID_PPV_ARGS(&graphicsAnalysis));
- if (SUCCEEDED(result))
- {
- underCapture = (graphicsAnalysis != nullptr);
- }
-
- SafeRelease(graphicsAnalysis);
- triedIDXGraphicsAnalysis = true;
- }
-
- return underCapture;
-#else
- // We can't detect GetStatus() on release WinRT 8.1 builds, so always return true.
- return true;
-#endif // (NTDDI_VERSION == NTDDI_WIN10) or _DEBUG
#else
// We can't detect GetStatus() on desktop ANGLE builds so always return true.
return true;
@@ -141,14 +101,13 @@ void DebugAnnotator11::initializeDevice()
HRESULT hr = E_FAIL;
// Create a D3D_DRIVER_TYPE_NULL device, which is much cheaper than other types of device.
- hr = D3D11CreateDevice(NULL, D3D_DRIVER_TYPE_NULL, nullptr, 0, nullptr, 0, D3D11_SDK_VERSION, &device, nullptr, &context);
+ hr = D3D11CreateDevice(nullptr, D3D_DRIVER_TYPE_NULL, nullptr, 0, nullptr, 0,
+ D3D11_SDK_VERSION, &device, nullptr, &context);
ASSERT(SUCCEEDED(hr));
if (SUCCEEDED(hr))
{
-#if defined(ANGLE_ENABLE_D3D11_1)
mUserDefinedAnnotation = d3d11::DynamicCastComObject<ID3DUserDefinedAnnotation>(context);
ASSERT(mUserDefinedAnnotation != nullptr);
-#endif
mInitialized = true;
}
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/DebugAnnotator11.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/DebugAnnotator11.h
index d1a0f7fd2e..62662c49ae 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/DebugAnnotator11.h
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/DebugAnnotator11.h
@@ -9,14 +9,12 @@
#ifndef LIBANGLE_RENDERER_D3D_D3D11_DEBUGANNOTATOR11_H_
#define LIBANGLE_RENDERER_D3D_D3D11_DEBUGANNOTATOR11_H_
-#include "common/debug.h"
-
-struct ID3DUserDefinedAnnotation;
+#include "libANGLE/LoggingAnnotator.h"
namespace rx
{
-class DebugAnnotator11 : public gl::DebugAnnotator
+class DebugAnnotator11 : public angle::LoggingAnnotator
{
public:
DebugAnnotator11();
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Fence11.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Fence11.cpp
index 53fac65f2a..082f28d794 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Fence11.cpp
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Fence11.cpp
@@ -4,7 +4,8 @@
// found in the LICENSE file.
//
-// Fence11.cpp: Defines the rx::FenceNV11 and rx::FenceSync11 classes which implement rx::FenceNVImpl and rx::FenceSyncImpl.
+// Fence11.cpp: Defines the rx::FenceNV11 and rx::Sync11 classes which implement
+// rx::FenceNVImpl and rx::SyncImpl.
#include "libANGLE/renderer/d3d/d3d11/Fence11.h"
#include "libANGLE/renderer/d3d/d3d11/Renderer11.h"
@@ -14,28 +15,30 @@
namespace rx
{
+static const int kDeviceLostCheckPeriod = 64;
+
//
// Template helpers for set and test operations.
//
-template<class FenceClass>
+template <class FenceClass>
gl::Error FenceSetHelper(FenceClass *fence)
{
if (!fence->mQuery)
{
D3D11_QUERY_DESC queryDesc;
- queryDesc.Query = D3D11_QUERY_EVENT;
+ queryDesc.Query = D3D11_QUERY_EVENT;
queryDesc.MiscFlags = 0;
HRESULT result = fence->mRenderer->getDevice()->CreateQuery(&queryDesc, &fence->mQuery);
if (FAILED(result))
{
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create event query, result: 0x%X.", result);
+ return gl::OutOfMemory() << "Failed to create event query, " << gl::FmtHR(result);
}
}
fence->mRenderer->getDeviceContext()->End(fence->mQuery);
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
template <class FenceClass>
@@ -44,30 +47,24 @@ gl::Error FenceTestHelper(FenceClass *fence, bool flushCommandBuffer, GLboolean
ASSERT(fence->mQuery);
UINT getDataFlags = (flushCommandBuffer ? 0 : D3D11_ASYNC_GETDATA_DONOTFLUSH);
- HRESULT result = fence->mRenderer->getDeviceContext()->GetData(fence->mQuery, NULL, 0, getDataFlags);
+ HRESULT result =
+ fence->mRenderer->getDeviceContext()->GetData(fence->mQuery, nullptr, 0, getDataFlags);
if (FAILED(result))
{
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to get query data, result: 0x%X.", result);
- }
- else if (fence->mRenderer->isDeviceLost())
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Device was lost while querying result of an event query.");
+ return gl::OutOfMemory() << "Failed to get query data, " << gl::FmtHR(result);
}
ASSERT(result == S_OK || result == S_FALSE);
*outFinished = ((result == S_OK) ? GL_TRUE : GL_FALSE);
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
//
// FenceNV11
//
-FenceNV11::FenceNV11(Renderer11 *renderer)
- : FenceNVImpl(),
- mRenderer(renderer),
- mQuery(NULL)
+FenceNV11::FenceNV11(Renderer11 *renderer) : FenceNVImpl(), mRenderer(renderer), mQuery(nullptr)
{
}
@@ -89,22 +86,26 @@ gl::Error FenceNV11::test(GLboolean *outFinished)
gl::Error FenceNV11::finish()
{
GLboolean finished = GL_FALSE;
+
+ int loopCount = 0;
while (finished != GL_TRUE)
{
- gl::Error error = FenceTestHelper(this, true, &finished);
- if (error.isError())
+ loopCount++;
+ ANGLE_TRY(FenceTestHelper(this, true, &finished));
+
+ if (loopCount % kDeviceLostCheckPeriod == 0 && mRenderer->testDeviceLost())
{
- return error;
+ return gl::OutOfMemory() << "Device was lost while querying result of an event query.";
}
ScheduleYield();
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
//
-// FenceSync11
+// Sync11
//
// Important note on accurate timers in Windows:
@@ -118,38 +119,34 @@ gl::Error FenceNV11::finish()
// We still opt to use QPC. In the present and moving forward, most newer systems will not suffer
// from buggy implementations.
-FenceSync11::FenceSync11(Renderer11 *renderer)
- : FenceSyncImpl(),
- mRenderer(renderer),
- mQuery(NULL)
+Sync11::Sync11(Renderer11 *renderer) : SyncImpl(), mRenderer(renderer), mQuery(nullptr)
{
LARGE_INTEGER counterFreqency = {};
- BOOL success = QueryPerformanceFrequency(&counterFreqency);
- UNUSED_ASSERTION_VARIABLE(success);
+ BOOL success = QueryPerformanceFrequency(&counterFreqency);
ASSERT(success);
mCounterFrequency = counterFreqency.QuadPart;
}
-FenceSync11::~FenceSync11()
+Sync11::~Sync11()
{
SafeRelease(mQuery);
}
-gl::Error FenceSync11::set(GLenum condition, GLbitfield flags)
+gl::Error Sync11::set(GLenum condition, GLbitfield flags)
{
ASSERT(condition == GL_SYNC_GPU_COMMANDS_COMPLETE && flags == 0);
return FenceSetHelper(this);
}
-gl::Error FenceSync11::clientWait(GLbitfield flags, GLuint64 timeout, GLenum *outResult)
+gl::Error Sync11::clientWait(GLbitfield flags, GLuint64 timeout, GLenum *outResult)
{
ASSERT(outResult);
bool flushCommandBuffer = ((flags & GL_SYNC_FLUSH_COMMANDS_BIT) != 0);
GLboolean result = GL_FALSE;
- gl::Error error = FenceTestHelper(this, flushCommandBuffer, &result);
+ gl::Error error = FenceTestHelper(this, flushCommandBuffer, &result);
if (error.isError())
{
*outResult = GL_WAIT_FAILED;
@@ -159,28 +156,34 @@ gl::Error FenceSync11::clientWait(GLbitfield flags, GLuint64 timeout, GLenum *ou
if (result == GL_TRUE)
{
*outResult = GL_ALREADY_SIGNALED;
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
if (timeout == 0)
{
*outResult = GL_TIMEOUT_EXPIRED;
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
LARGE_INTEGER currentCounter = {};
- BOOL success = QueryPerformanceCounter(&currentCounter);
- UNUSED_ASSERTION_VARIABLE(success);
+ BOOL success = QueryPerformanceCounter(&currentCounter);
ASSERT(success);
- LONGLONG timeoutInSeconds = static_cast<LONGLONG>(timeout) * static_cast<LONGLONG>(1000000ll);
- LONGLONG endCounter = currentCounter.QuadPart + mCounterFrequency * timeoutInSeconds;
+ LONGLONG timeoutInSeconds = static_cast<LONGLONG>(timeout / 1000000000ull);
+ LONGLONG endCounter = currentCounter.QuadPart + mCounterFrequency * timeoutInSeconds;
+ // Extremely unlikely, but if mCounterFrequency is large enough, endCounter can wrap
+ if (endCounter < currentCounter.QuadPart)
+ {
+ endCounter = MAXLONGLONG;
+ }
+
+ int loopCount = 0;
while (currentCounter.QuadPart < endCounter && !result)
{
+ loopCount++;
ScheduleYield();
success = QueryPerformanceCounter(&currentCounter);
- UNUSED_ASSERTION_VARIABLE(success);
ASSERT(success);
error = FenceTestHelper(this, flushCommandBuffer, &result);
@@ -189,6 +192,12 @@ gl::Error FenceSync11::clientWait(GLbitfield flags, GLuint64 timeout, GLenum *ou
*outResult = GL_WAIT_FAILED;
return error;
}
+
+ if ((loopCount % kDeviceLostCheckPeriod) == 0 && mRenderer->testDeviceLost())
+ {
+ *outResult = GL_WAIT_FAILED;
+ return gl::OutOfMemory() << "Device was lost while querying result of an event query.";
+ }
}
if (currentCounter.QuadPart >= endCounter)
@@ -200,32 +209,32 @@ gl::Error FenceSync11::clientWait(GLbitfield flags, GLuint64 timeout, GLenum *ou
*outResult = GL_CONDITION_SATISFIED;
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error FenceSync11::serverWait(GLbitfield flags, GLuint64 timeout)
+gl::Error Sync11::serverWait(GLbitfield flags, GLuint64 timeout)
{
// Because our API is currently designed to be called from a single thread, we don't need to do
- // extra work for a server-side fence. GPU commands issued after the fence is created will always
- // be processed after the fence is signaled.
- return gl::Error(GL_NO_ERROR);
+ // extra work for a server-side fence. GPU commands issued after the fence is created will
+ // always be processed after the fence is signaled.
+ return gl::NoError();
}
-gl::Error FenceSync11::getStatus(GLint *outResult)
+gl::Error Sync11::getStatus(GLint *outResult)
{
GLboolean result = GL_FALSE;
- gl::Error error = FenceTestHelper(this, false, &result);
+ gl::Error error = FenceTestHelper(this, false, &result);
if (error.isError())
{
- // The spec does not specify any way to report errors during the status test (e.g. device lost)
- // so we report the fence is unblocked in case of error or signaled.
+ // The spec does not specify any way to report errors during the status test (e.g. device
+ // lost) so we report the fence is unblocked in case of error or signaled.
*outResult = GL_SIGNALED;
return error;
}
*outResult = (result ? GL_SIGNALED : GL_UNSIGNALED);
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-} // namespace rx
+} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Fence11.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Fence11.h
index 595978885b..4168df5365 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Fence11.h
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Fence11.h
@@ -4,13 +4,14 @@
// found in the LICENSE file.
//
-// Fence11.h: Defines the rx::FenceNV11 and rx::FenceSync11 classes which implement rx::FenceNVImpl and rx::FenceSyncImpl.
+// Fence11.h: Defines the rx::FenceNV11 and rx::Sync11 classes which implement rx::FenceNVImpl
+// and rx::SyncImpl.
#ifndef LIBANGLE_RENDERER_D3D_D3D11_FENCE11_H_
#define LIBANGLE_RENDERER_D3D_D3D11_FENCE11_H_
#include "libANGLE/renderer/FenceNVImpl.h"
-#include "libANGLE/renderer/FenceSyncImpl.h"
+#include "libANGLE/renderer/SyncImpl.h"
namespace rx
{
@@ -34,11 +35,11 @@ class FenceNV11 : public FenceNVImpl
ID3D11Query *mQuery;
};
-class FenceSync11 : public FenceSyncImpl
+class Sync11 : public SyncImpl
{
public:
- explicit FenceSync11(Renderer11 *renderer);
- ~FenceSync11() override;
+ explicit Sync11(Renderer11 *renderer);
+ ~Sync11() override;
gl::Error set(GLenum condition, GLbitfield flags) override;
gl::Error clientWait(GLbitfield flags, GLuint64 timeout, GLenum *outResult) override;
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Framebuffer11.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Framebuffer11.cpp
index 186a035902..02326d7b50 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Framebuffer11.cpp
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Framebuffer11.cpp
@@ -8,94 +8,119 @@
#include "libANGLE/renderer/d3d/d3d11/Framebuffer11.h"
+#include "common/bitset_utils.h"
#include "common/debug.h"
+#include "libANGLE/Context.h"
+#include "libANGLE/Framebuffer.h"
+#include "libANGLE/FramebufferAttachment.h"
+#include "libANGLE/Texture.h"
+#include "libANGLE/renderer/d3d/TextureD3D.h"
#include "libANGLE/renderer/d3d/d3d11/Buffer11.h"
#include "libANGLE/renderer/d3d/d3d11/Clear11.h"
-#include "libANGLE/renderer/d3d/d3d11/TextureStorage11.h"
-#include "libANGLE/renderer/d3d/d3d11/Renderer11.h"
-#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
#include "libANGLE/renderer/d3d/d3d11/RenderTarget11.h"
+#include "libANGLE/renderer/d3d/d3d11/Renderer11.h"
+#include "libANGLE/renderer/d3d/d3d11/TextureStorage11.h"
#include "libANGLE/renderer/d3d/d3d11/formatutils11.h"
-#include "libANGLE/renderer/d3d/TextureD3D.h"
-#include "libANGLE/Framebuffer.h"
-#include "libANGLE/FramebufferAttachment.h"
-#include "libANGLE/Texture.h"
+#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
+
+using namespace angle;
namespace rx
{
-Framebuffer11::Framebuffer11(const gl::Framebuffer::Data &data, Renderer11 *renderer)
- : FramebufferD3D(data, renderer), mRenderer(renderer)
+namespace
{
- ASSERT(mRenderer != nullptr);
-}
-
-Framebuffer11::~Framebuffer11()
+gl::Error MarkAttachmentsDirty(const gl::Context *context,
+ const gl::FramebufferAttachment *attachment)
{
-}
-
-static gl::Error InvalidateAttachmentSwizzles(const gl::FramebufferAttachment *attachment)
-{
- if (attachment && attachment->type() == GL_TEXTURE)
+ if (attachment->type() == GL_TEXTURE)
{
gl::Texture *texture = attachment->getTexture();
TextureD3D *textureD3D = GetImplAs<TextureD3D>(texture);
TextureStorage *texStorage = nullptr;
- gl::Error error = textureD3D->getNativeTexture(&texStorage);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(textureD3D->getNativeTexture(context, &texStorage));
if (texStorage)
{
TextureStorage11 *texStorage11 = GetAs<TextureStorage11>(texStorage);
ASSERT(texStorage11);
- texStorage11->invalidateSwizzleCacheLevel(attachment->mipLevel());
+ texStorage11->markLevelDirty(attachment->mipLevel());
}
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error Framebuffer11::invalidateSwizzles() const
+void UpdateCachedRenderTarget(const gl::Context *context,
+ const gl::FramebufferAttachment *attachment,
+ RenderTarget11 *&cachedRenderTarget,
+ OnRenderTargetDirtyBinding *channelBinding)
{
- for (const auto &colorAttachment : mData.getColorAttachments())
+ RenderTarget11 *newRenderTarget = nullptr;
+ if (attachment)
{
- if (colorAttachment.isAttached())
+ // TODO(jmadill): Don't swallow this error.
+ gl::Error error = attachment->getRenderTarget(context, &newRenderTarget);
+ if (error.isError())
{
- gl::Error error = InvalidateAttachmentSwizzles(&colorAttachment);
- if (error.isError())
- {
- return error;
- }
+ ERR() << "Internal rendertarget error: " << error;
}
}
+ if (newRenderTarget != cachedRenderTarget)
+ {
+ OnRenderTargetDirtyChannel *channel =
+ (newRenderTarget ? newRenderTarget->getBroadcastChannel() : nullptr);
+ channelBinding->bind(channel);
+ cachedRenderTarget = newRenderTarget;
+ }
+}
+} // anonymous namespace
+
+Framebuffer11::Framebuffer11(const gl::FramebufferState &data, Renderer11 *renderer)
+ : FramebufferD3D(data, renderer),
+ mRenderer(renderer),
+ mCachedDepthStencilRenderTarget(nullptr),
+ mDepthStencilRenderTargetDirty(this, gl::IMPLEMENTATION_MAX_FRAMEBUFFER_ATTACHMENTS)
+{
+ ASSERT(mRenderer != nullptr);
+ mCachedColorRenderTargets.fill(nullptr);
+ for (size_t colorIndex = 0; colorIndex < data.getColorAttachments().size(); ++colorIndex)
+ {
+ mColorRenderTargetsDirty.emplace_back(this, colorIndex);
+ }
+}
- gl::Error error = InvalidateAttachmentSwizzles(mData.getDepthAttachment());
- if (error.isError())
+Framebuffer11::~Framebuffer11()
+{
+}
+
+gl::Error Framebuffer11::markAttachmentsDirty(const gl::Context *context) const
+{
+ const auto &colorAttachments = mState.getColorAttachments();
+ for (size_t drawBuffer : mState.getEnabledDrawBuffers())
{
- return error;
+ const gl::FramebufferAttachment &colorAttachment = colorAttachments[drawBuffer];
+ ASSERT(colorAttachment.isAttached());
+ ANGLE_TRY(MarkAttachmentsDirty(context, &colorAttachment));
}
- error = InvalidateAttachmentSwizzles(mData.getStencilAttachment());
- if (error.isError())
+ const gl::FramebufferAttachment *dsAttachment = mState.getDepthOrStencilAttachment();
+ if (dsAttachment)
{
- return error;
+ ANGLE_TRY(MarkAttachmentsDirty(context, dsAttachment));
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error Framebuffer11::clear(const gl::Data &data, const ClearParameters &clearParams)
+gl::Error Framebuffer11::clearImpl(const gl::Context *context, const ClearParameters &clearParams)
{
Clear11 *clearer = mRenderer->getClearer();
- gl::Error error(GL_NO_ERROR);
- const gl::FramebufferAttachment *colorAttachment = mData.getFirstColorAttachment();
+ const gl::FramebufferAttachment *colorAttachment = mState.getFirstColorAttachment();
if (clearParams.scissorEnabled == true && colorAttachment != nullptr &&
UsePresentPathFast(mRenderer, colorAttachment))
{
@@ -107,46 +132,43 @@ gl::Error Framebuffer11::clear(const gl::Data &data, const ClearParameters &clea
presentPathFastClearParams.scissor.y = framebufferSize.height -
presentPathFastClearParams.scissor.y -
presentPathFastClearParams.scissor.height;
- error = clearer->clearFramebuffer(presentPathFastClearParams, mData);
+ ANGLE_TRY(clearer->clearFramebuffer(context, presentPathFastClearParams, mState));
}
else
{
- error = clearer->clearFramebuffer(clearParams, mData);
+ ANGLE_TRY(clearer->clearFramebuffer(context, clearParams, mState));
}
- if (error.isError())
- {
- return error;
- }
-
- error = invalidateSwizzles();
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(markAttachmentsDirty(context));
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error Framebuffer11::invalidate(size_t count, const GLenum *attachments)
+gl::Error Framebuffer11::invalidate(const gl::Context *context,
+ size_t count,
+ const GLenum *attachments)
{
- return invalidateBase(count, attachments, false);
+ return invalidateBase(context, count, attachments, false);
}
-gl::Error Framebuffer11::discard(size_t count, const GLenum *attachments)
+gl::Error Framebuffer11::discard(const gl::Context *context,
+ size_t count,
+ const GLenum *attachments)
{
- return invalidateBase(count, attachments, true);
+ return invalidateBase(context, count, attachments, true);
}
-gl::Error Framebuffer11::invalidateBase(size_t count, const GLenum *attachments, bool useEXTBehavior) const
+gl::Error Framebuffer11::invalidateBase(const gl::Context *context,
+ size_t count,
+ const GLenum *attachments,
+ bool useEXTBehavior) const
{
-#if defined(ANGLE_ENABLE_D3D11_1)
ID3D11DeviceContext1 *deviceContext1 = mRenderer->getDeviceContext1IfSupported();
if (!deviceContext1)
{
// DiscardView() is only supported on ID3D11DeviceContext1
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
bool foundDepth = false;
@@ -175,37 +197,14 @@ gl::Error Framebuffer11::invalidateBase(size_t count, const GLenum *attachments,
ASSERT((attachments[i] >= GL_COLOR_ATTACHMENT0 && attachments[i] <= GL_COLOR_ATTACHMENT15) ||
(attachments[i] == GL_COLOR));
- RenderTarget11 *renderTarget = nullptr;
- ID3D11View *colorView = nullptr;
- gl::Error error(GL_NO_ERROR);
- size_t colorAttachmentID = 0;
-
- if (attachments[i] == GL_COLOR)
- {
- colorAttachmentID = 0;
- }
- else
+ size_t colorIndex =
+ (attachments[i] == GL_COLOR ? 0u : (attachments[i] - GL_COLOR_ATTACHMENT0));
+ const gl::FramebufferAttachment *colorAttachment =
+ mState.getColorAttachment(colorIndex);
+ if (colorAttachment)
{
- colorAttachmentID = attachments[i] - GL_COLOR_ATTACHMENT0;
+ ANGLE_TRY(invalidateAttachment(context, colorAttachment));
}
-
- if (mData.getColorAttachment(static_cast<unsigned int>(colorAttachmentID)))
- {
- error = mData.getColorAttachment(static_cast<unsigned int>(colorAttachmentID))
- ->getRenderTarget(&renderTarget);
- if (error.isError())
- {
- return error;
- }
-
- colorView = renderTarget->getRenderTargetView();
-
- if (colorView != nullptr)
- {
- deviceContext1->DiscardView(colorView);
- }
- }
-
break;
}
}
@@ -222,7 +221,7 @@ gl::Error Framebuffer11::invalidateBase(size_t count, const GLenum *attachments,
discardDepth = foundDepth;
// Don't bother discarding the stencil buffer if the depth buffer will already do it
- discardStencil = foundStencil && (!discardDepth || mData.getDepthAttachment() == nullptr);
+ discardStencil = foundStencil && (!discardDepth || mState.getDepthAttachment() == nullptr);
}
else
{
@@ -230,94 +229,86 @@ gl::Error Framebuffer11::invalidateBase(size_t count, const GLenum *attachments,
// attachments list does not include DEPTH_STENCIL_ATTACHMENT or both DEPTH_ATTACHMENT and
// STENCIL_ATTACHMENT, then only the specified portion of every pixel in the subregion of pixels
// of the DEPTH_STENCIL buffer may be invalidated, and the other portion must be preserved.
- discardDepth = (foundDepth && foundStencil) || (foundDepth && (mData.getStencilAttachment() == nullptr));
- discardStencil = (foundStencil && (mData.getDepthAttachment() == nullptr));
+ discardDepth = (foundDepth && foundStencil) ||
+ (foundDepth && (mState.getStencilAttachment() == nullptr));
+ discardStencil = (foundStencil && (mState.getDepthAttachment() == nullptr));
}
- if (discardDepth && mData.getDepthAttachment())
+ if (discardDepth && mState.getDepthAttachment())
{
- RenderTarget11 *renderTarget = nullptr;
- ID3D11View *depthView = nullptr;
- gl::Error error(GL_NO_ERROR);
-
- error = mData.getDepthAttachment()->getRenderTarget(&renderTarget);
- if (error.isError())
- {
- return error;
- }
-
- depthView = renderTarget->getDepthStencilView();
-
- if (depthView != nullptr)
- {
- deviceContext1->DiscardView(depthView);
- }
+ ANGLE_TRY(invalidateAttachment(context, mState.getDepthAttachment()));
}
- if (discardStencil && mData.getStencilAttachment())
+ if (discardStencil && mState.getStencilAttachment())
{
- RenderTarget11 *renderTarget = nullptr;
- ID3D11View *stencilView = nullptr;
- gl::Error error(GL_NO_ERROR);
-
- error = mData.getStencilAttachment()->getRenderTarget(&renderTarget);
- if (error.isError())
- {
- return error;
- }
-
- stencilView = renderTarget->getDepthStencilView();
-
- if (stencilView != nullptr)
- {
- deviceContext1->DiscardView(stencilView);
- }
+ ANGLE_TRY(invalidateAttachment(context, mState.getStencilAttachment()));
}
-#endif // ANGLE_ENABLE_D3D11_1
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error Framebuffer11::invalidateSub(size_t, const GLenum *, const gl::Rectangle &)
+gl::Error Framebuffer11::invalidateSub(const gl::Context *context,
+ size_t,
+ const GLenum *,
+ const gl::Rectangle &)
{
// A no-op implementation conforms to the spec, so don't call UNIMPLEMENTED()
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error Framebuffer11::readPixelsImpl(const gl::Rectangle &area,
+gl::Error Framebuffer11::invalidateAttachment(const gl::Context *context,
+ const gl::FramebufferAttachment *attachment) const
+{
+ ID3D11DeviceContext1 *deviceContext1 = mRenderer->getDeviceContext1IfSupported();
+ ASSERT(deviceContext1);
+ ASSERT(attachment && attachment->isAttached());
+
+ RenderTarget11 *renderTarget = nullptr;
+ ANGLE_TRY(attachment->getRenderTarget(context, &renderTarget));
+ const auto &rtv = renderTarget->getRenderTargetView();
+
+ if (rtv.valid())
+ {
+ deviceContext1->DiscardView(rtv.get());
+ }
+
+ return gl::NoError();
+}
+
+gl::Error Framebuffer11::readPixelsImpl(const gl::Context *context,
+ const gl::Rectangle &area,
GLenum format,
GLenum type,
size_t outputPitch,
const gl::PixelPackState &pack,
- uint8_t *pixels) const
+ uint8_t *pixels)
{
- const gl::FramebufferAttachment *readAttachment = mData.getReadAttachment();
+ const gl::FramebufferAttachment *readAttachment = mState.getReadAttachment();
ASSERT(readAttachment);
- gl::Buffer *packBuffer = pack.pixelBuffer.get();
+ gl::Buffer *packBuffer = context->getGLState().getTargetBuffer(gl::BufferBinding::PixelPack);
if (packBuffer != nullptr)
{
- if (pack.rowLength != 0 || pack.skipRows != 0 || pack.skipPixels != 0)
- {
- UNIMPLEMENTED();
- return gl::Error(GL_INVALID_OPERATION,
- "Unimplemented pixel store parameters in readPixelsImpl");
- }
-
Buffer11 *packBufferStorage = GetImplAs<Buffer11>(packBuffer);
PackPixelsParams packParams(area, format, type, static_cast<GLuint>(outputPitch), pack,
- reinterpret_cast<ptrdiff_t>(pixels));
+ packBuffer, reinterpret_cast<ptrdiff_t>(pixels));
- return packBufferStorage->packPixels(*readAttachment, packParams);
+ return packBufferStorage->packPixels(context, *readAttachment, packParams);
}
- return mRenderer->readFromAttachment(*readAttachment, area, format, type,
+ return mRenderer->readFromAttachment(context, *readAttachment, area, format, type,
static_cast<GLuint>(outputPitch), pack, pixels);
}
-gl::Error Framebuffer11::blit(const gl::Rectangle &sourceArea, const gl::Rectangle &destArea, const gl::Rectangle *scissor,
- bool blitRenderTarget, bool blitDepth, bool blitStencil, GLenum filter,
- const gl::Framebuffer *sourceFramebuffer)
+gl::Error Framebuffer11::blitImpl(const gl::Context *context,
+ const gl::Rectangle &sourceArea,
+ const gl::Rectangle &destArea,
+ const gl::Rectangle *scissor,
+ bool blitRenderTarget,
+ bool blitDepth,
+ bool blitStencil,
+ GLenum filter,
+ const gl::Framebuffer *sourceFramebuffer)
{
if (blitRenderTarget)
{
@@ -325,15 +316,11 @@ gl::Error Framebuffer11::blit(const gl::Rectangle &sourceArea, const gl::Rectang
ASSERT(readBuffer);
RenderTargetD3D *readRenderTarget = nullptr;
- gl::Error error = readBuffer->getRenderTarget(&readRenderTarget);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(readBuffer->getRenderTarget(context, &readRenderTarget));
ASSERT(readRenderTarget);
- const auto &colorAttachments = mData.getColorAttachments();
- const auto &drawBufferStates = mData.getDrawBufferStates();
+ const auto &colorAttachments = mState.getColorAttachments();
+ const auto &drawBufferStates = mState.getDrawBufferStates();
for (size_t colorAttachment = 0; colorAttachment < colorAttachments.size(); colorAttachment++)
{
@@ -343,11 +330,7 @@ gl::Error Framebuffer11::blit(const gl::Rectangle &sourceArea, const gl::Rectang
drawBufferStates[colorAttachment] != GL_NONE)
{
RenderTargetD3D *drawRenderTarget = nullptr;
- error = drawBuffer.getRenderTarget(&drawRenderTarget);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(drawBuffer.getRenderTarget(context, &drawRenderTarget));
ASSERT(drawRenderTarget);
const bool invertColorSource = UsePresentPathFast(mRenderer, readBuffer);
@@ -368,13 +351,9 @@ gl::Error Framebuffer11::blit(const gl::Rectangle &sourceArea, const gl::Rectang
actualDestArea.height = -destArea.height;
}
- error = mRenderer->blitRenderbufferRect(actualSourceArea, actualDestArea,
- readRenderTarget, drawRenderTarget, filter,
- scissor, blitRenderTarget, false, false);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(mRenderer->blitRenderbufferRect(
+ context, actualSourceArea, actualDestArea, readRenderTarget, drawRenderTarget,
+ filter, scissor, blitRenderTarget, false, false));
}
}
}
@@ -385,46 +364,144 @@ gl::Error Framebuffer11::blit(const gl::Rectangle &sourceArea, const gl::Rectang
ASSERT(readBuffer);
RenderTargetD3D *readRenderTarget = nullptr;
- gl::Error error = readBuffer->getRenderTarget(&readRenderTarget);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(readBuffer->getRenderTarget(context, &readRenderTarget));
ASSERT(readRenderTarget);
- const gl::FramebufferAttachment *drawBuffer = mData.getDepthOrStencilAttachment();
+ const gl::FramebufferAttachment *drawBuffer = mState.getDepthOrStencilAttachment();
ASSERT(drawBuffer);
RenderTargetD3D *drawRenderTarget = nullptr;
- error = drawBuffer->getRenderTarget(&drawRenderTarget);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(drawBuffer->getRenderTarget(context, &drawRenderTarget));
ASSERT(drawRenderTarget);
- error = mRenderer->blitRenderbufferRect(sourceArea, destArea, readRenderTarget, drawRenderTarget, filter, scissor,
- false, blitDepth, blitStencil);
- if (error.isError())
+ ANGLE_TRY(mRenderer->blitRenderbufferRect(context, sourceArea, destArea, readRenderTarget,
+ drawRenderTarget, filter, scissor, false,
+ blitDepth, blitStencil));
+ }
+
+ ANGLE_TRY(markAttachmentsDirty(context));
+ return gl::NoError();
+}
+
+GLenum Framebuffer11::getRenderTargetImplementationFormat(RenderTargetD3D *renderTarget) const
+{
+ RenderTarget11 *renderTarget11 = GetAs<RenderTarget11>(renderTarget);
+ return renderTarget11->getFormatSet().format().fboImplementationInternalFormat;
+}
+
+void Framebuffer11::updateColorRenderTarget(const gl::Context *context, size_t colorIndex)
+{
+ UpdateCachedRenderTarget(context, mState.getColorAttachment(colorIndex),
+ mCachedColorRenderTargets[colorIndex],
+ &mColorRenderTargetsDirty[colorIndex]);
+}
+
+void Framebuffer11::updateDepthStencilRenderTarget(const gl::Context *context)
+{
+ UpdateCachedRenderTarget(context, mState.getDepthOrStencilAttachment(),
+ mCachedDepthStencilRenderTarget, &mDepthStencilRenderTargetDirty);
+}
+
+void Framebuffer11::syncState(const gl::Context *context,
+ const gl::Framebuffer::DirtyBits &dirtyBits)
+{
+ const auto &mergedDirtyBits = dirtyBits | mInternalDirtyBits;
+ mInternalDirtyBits.reset();
+
+ for (auto dirtyBit : mergedDirtyBits)
+ {
+ switch (dirtyBit)
{
- return error;
+ case gl::Framebuffer::DIRTY_BIT_DEPTH_ATTACHMENT:
+ case gl::Framebuffer::DIRTY_BIT_STENCIL_ATTACHMENT:
+ updateDepthStencilRenderTarget(context);
+ break;
+ case gl::Framebuffer::DIRTY_BIT_DRAW_BUFFERS:
+ case gl::Framebuffer::DIRTY_BIT_READ_BUFFER:
+ break;
+ case gl::Framebuffer::DIRTY_BIT_DEFAULT_WIDTH:
+ case gl::Framebuffer::DIRTY_BIT_DEFAULT_HEIGHT:
+ case gl::Framebuffer::DIRTY_BIT_DEFAULT_SAMPLES:
+ case gl::Framebuffer::DIRTY_BIT_DEFAULT_FIXED_SAMPLE_LOCATIONS:
+ break;
+ default:
+ {
+ ASSERT(gl::Framebuffer::DIRTY_BIT_COLOR_ATTACHMENT_0 == 0 &&
+ dirtyBit < gl::Framebuffer::DIRTY_BIT_COLOR_ATTACHMENT_MAX);
+ size_t colorIndex =
+ static_cast<size_t>(dirtyBit - gl::Framebuffer::DIRTY_BIT_COLOR_ATTACHMENT_0);
+ updateColorRenderTarget(context, colorIndex);
+ break;
+ }
}
}
- gl::Error error = invalidateSwizzles();
- if (error.isError())
+ // We should not have dirtied any additional state during our sync.
+ ASSERT(!mInternalDirtyBits.any());
+
+ FramebufferD3D::syncState(context, dirtyBits);
+
+ // Call this last to allow the state manager to take advantage of the cached render targets.
+ mRenderer->getStateManager()->invalidateRenderTarget();
+
+ // Call this to syncViewport for framebuffer default parameters.
+ if (mState.getDefaultWidth() != 0 || mState.getDefaultHeight() != 0)
+ {
+ mRenderer->getStateManager()->invalidateViewport(context);
+ }
+}
+
+void Framebuffer11::signal(size_t channelID, const gl::Context *context)
+{
+ if (channelID == gl::IMPLEMENTATION_MAX_FRAMEBUFFER_ATTACHMENTS)
+ {
+ // Stencil is redundant in this case.
+ mInternalDirtyBits.set(gl::Framebuffer::DIRTY_BIT_DEPTH_ATTACHMENT);
+ mCachedDepthStencilRenderTarget = nullptr;
+ }
+ else
{
- return error;
+ mInternalDirtyBits.set(gl::Framebuffer::DIRTY_BIT_COLOR_ATTACHMENT_0 + channelID);
+ mCachedColorRenderTargets[channelID] = nullptr;
}
- return gl::Error(GL_NO_ERROR);
+ // Notify the context we need to re-validate the RenderTarget.
+ // TODO(jmadill): Check that we're the active draw framebuffer.
+ mRenderer->getStateManager()->invalidateRenderTarget();
}
-GLenum Framebuffer11::getRenderTargetImplementationFormat(RenderTargetD3D *renderTarget) const
+gl::Error Framebuffer11::getSamplePosition(size_t index, GLfloat *xy) const
{
- RenderTarget11 *renderTarget11 = GetAs<RenderTarget11>(renderTarget);
- const d3d11::DXGIFormat &dxgiFormatInfo = d3d11::GetDXGIFormatInfo(renderTarget11->getDXGIFormat());
- return dxgiFormatInfo.internalFormat;
+ const gl::FramebufferAttachment *attachment = mState.getFirstNonNullAttachment();
+ ASSERT(attachment);
+ GLsizei sampleCount = attachment->getSamples();
+
+ d3d11_gl::GetSamplePosition(sampleCount, index, xy);
+ return gl::NoError();
+}
+
+bool Framebuffer11::hasAnyInternalDirtyBit() const
+{
+ return mInternalDirtyBits.any();
+}
+
+void Framebuffer11::syncInternalState(const gl::Context *context)
+{
+ syncState(context, gl::Framebuffer::DirtyBits());
}
+RenderTarget11 *Framebuffer11::getFirstRenderTarget() const
+{
+ ASSERT(mInternalDirtyBits.none());
+ for (auto *renderTarget : mCachedColorRenderTargets)
+ {
+ if (renderTarget)
+ {
+ return renderTarget;
+ }
+ }
+
+ return mCachedDepthStencilRenderTarget;
}
+
+} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Framebuffer11.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Framebuffer11.h
index c8a33ec7e5..afdda299b9 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Framebuffer11.h
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Framebuffer11.h
@@ -10,43 +10,93 @@
#define LIBANGLE_RENDERER_D3D_D3D11_FRAMBUFFER11_H_
#include "libANGLE/renderer/d3d/FramebufferD3D.h"
+#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
+#include "libANGLE/signal_utils.h"
namespace rx
{
class Renderer11;
-class Framebuffer11 : public FramebufferD3D
+class Framebuffer11 : public FramebufferD3D, public OnRenderTargetDirtyReceiver
{
public:
- Framebuffer11(const gl::Framebuffer::Data &data, Renderer11 *renderer);
- virtual ~Framebuffer11();
+ Framebuffer11(const gl::FramebufferState &data, Renderer11 *renderer);
+ ~Framebuffer11() override;
- gl::Error discard(size_t count, const GLenum *attachments) override;
- gl::Error invalidate(size_t count, const GLenum *attachments) override;
- gl::Error invalidateSub(size_t count, const GLenum *attachments, const gl::Rectangle &area) override;
+ gl::Error discard(const gl::Context *context, size_t count, const GLenum *attachments) override;
+ gl::Error invalidate(const gl::Context *context,
+ size_t count,
+ const GLenum *attachments) override;
+ gl::Error invalidateSub(const gl::Context *context,
+ size_t count,
+ const GLenum *attachments,
+ const gl::Rectangle &area) override;
// Invalidate the cached swizzles of all bound texture attachments.
- gl::Error invalidateSwizzles() const;
+ gl::Error markAttachmentsDirty(const gl::Context *context) const;
+
+ void syncState(const gl::Context *context,
+ const gl::Framebuffer::DirtyBits &dirtyBits) override;
+
+ const RenderTargetArray &getCachedColorRenderTargets() const
+ {
+ return mCachedColorRenderTargets;
+ }
+ const RenderTarget11 *getCachedDepthStencilRenderTarget() const
+ {
+ return mCachedDepthStencilRenderTarget;
+ }
+
+ RenderTarget11 *getFirstRenderTarget() const;
+
+ bool hasAnyInternalDirtyBit() const;
+ void syncInternalState(const gl::Context *context);
+
+ void signal(size_t channelID, const gl::Context *context) override;
+
+ gl::Error getSamplePosition(size_t index, GLfloat *xy) const override;
private:
- gl::Error clear(const gl::Data &data, const ClearParameters &clearParams) override;
+ gl::Error clearImpl(const gl::Context *context, const ClearParameters &clearParams) override;
- gl::Error readPixelsImpl(const gl::Rectangle &area,
+ gl::Error readPixelsImpl(const gl::Context *context,
+ const gl::Rectangle &area,
GLenum format,
GLenum type,
size_t outputPitch,
const gl::PixelPackState &pack,
- uint8_t *pixels) const override;
+ uint8_t *pixels) override;
- gl::Error blit(const gl::Rectangle &sourceArea, const gl::Rectangle &destArea, const gl::Rectangle *scissor,
- bool blitRenderTarget, bool blitDepth, bool blitStencil, GLenum filter,
- const gl::Framebuffer *sourceFramebuffer) override;
+ gl::Error blitImpl(const gl::Context *context,
+ const gl::Rectangle &sourceArea,
+ const gl::Rectangle &destArea,
+ const gl::Rectangle *scissor,
+ bool blitRenderTarget,
+ bool blitDepth,
+ bool blitStencil,
+ GLenum filter,
+ const gl::Framebuffer *sourceFramebuffer) override;
- gl::Error invalidateBase(size_t count, const GLenum *attachments, bool useEXTBehavior) const;
+ gl::Error invalidateBase(const gl::Context *context,
+ size_t count,
+ const GLenum *attachments,
+ bool useEXTBehavior) const;
+ gl::Error invalidateAttachment(const gl::Context *context,
+ const gl::FramebufferAttachment *attachment) const;
GLenum getRenderTargetImplementationFormat(RenderTargetD3D *renderTarget) const override;
+ void updateColorRenderTarget(const gl::Context *context, size_t colorIndex);
+ void updateDepthStencilRenderTarget(const gl::Context *context);
+
Renderer11 *const mRenderer;
+ RenderTargetArray mCachedColorRenderTargets;
+ RenderTarget11 *mCachedDepthStencilRenderTarget;
+
+ std::vector<OnRenderTargetDirtyBinding> mColorRenderTargetsDirty;
+ OnRenderTargetDirtyBinding mDepthStencilRenderTargetDirty;
+
+ gl::Framebuffer::DirtyBits mInternalDirtyBits;
};
}
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Image11.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Image11.cpp
index c52092d81e..bd921f1935 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Image11.cpp
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Image11.cpp
@@ -26,10 +26,10 @@ namespace rx
Image11::Image11(Renderer11 *renderer)
: mRenderer(renderer),
mDXGIFormat(DXGI_FORMAT_UNKNOWN),
- mStagingTexture(NULL),
+ mStagingTexture(),
mStagingSubresource(0),
mRecoverFromStorage(false),
- mAssociatedStorage(NULL),
+ mAssociatedStorage(nullptr),
mAssociatedImageIndex(gl::ImageIndex::MakeInvalid()),
mRecoveredFromStorageCount(0)
{
@@ -41,55 +41,106 @@ Image11::~Image11()
releaseStagingTexture();
}
-gl::Error Image11::generateMipmap(Image11 *dest, Image11 *src)
+// static
+gl::Error Image11::GenerateMipmap(const gl::Context *context,
+ Image11 *dest,
+ Image11 *src,
+ const Renderer11DeviceCaps &rendererCaps)
{
ASSERT(src->getDXGIFormat() == dest->getDXGIFormat());
ASSERT(src->getWidth() == 1 || src->getWidth() / 2 == dest->getWidth());
ASSERT(src->getHeight() == 1 || src->getHeight() / 2 == dest->getHeight());
- const d3d11::DXGIFormat &dxgiFormatInfo = d3d11::GetDXGIFormatInfo(src->getDXGIFormat());
- ASSERT(dxgiFormatInfo.mipGenerationFunction != NULL);
-
D3D11_MAPPED_SUBRESOURCE destMapped;
- gl::Error error = dest->map(D3D11_MAP_WRITE, &destMapped);
+ ANGLE_TRY(dest->map(context, D3D11_MAP_WRITE, &destMapped));
+
+ D3D11_MAPPED_SUBRESOURCE srcMapped;
+ gl::Error error = src->map(context, D3D11_MAP_READ, &srcMapped);
if (error.isError())
{
+ dest->unmap();
return error;
}
+ const uint8_t *sourceData = reinterpret_cast<const uint8_t *>(srcMapped.pData);
+ uint8_t *destData = reinterpret_cast<uint8_t *>(destMapped.pData);
+
+ auto mipGenerationFunction =
+ d3d11::Format::Get(src->getInternalFormat(), rendererCaps).format().mipGenerationFunction;
+ mipGenerationFunction(src->getWidth(), src->getHeight(), src->getDepth(), sourceData,
+ srcMapped.RowPitch, srcMapped.DepthPitch, destData, destMapped.RowPitch,
+ destMapped.DepthPitch);
+
+ dest->unmap();
+ src->unmap();
+
+ dest->markDirty();
+
+ return gl::NoError();
+}
+
+// static
+gl::Error Image11::CopyImage(const gl::Context *context,
+ Image11 *dest,
+ Image11 *source,
+ const gl::Rectangle &sourceRect,
+ const gl::Offset &destOffset,
+ bool unpackFlipY,
+ bool unpackPremultiplyAlpha,
+ bool unpackUnmultiplyAlpha,
+ const Renderer11DeviceCaps &rendererCaps)
+{
+ D3D11_MAPPED_SUBRESOURCE destMapped;
+ ANGLE_TRY(dest->map(context, D3D11_MAP_WRITE, &destMapped));
+
D3D11_MAPPED_SUBRESOURCE srcMapped;
- error = src->map(D3D11_MAP_READ, &srcMapped);
+ gl::Error error = source->map(context, D3D11_MAP_READ, &srcMapped);
if (error.isError())
{
dest->unmap();
return error;
}
- const uint8_t *sourceData = reinterpret_cast<const uint8_t*>(srcMapped.pData);
- uint8_t *destData = reinterpret_cast<uint8_t*>(destMapped.pData);
+ const auto &sourceFormat =
+ d3d11::Format::Get(source->getInternalFormat(), rendererCaps).format();
+ GLuint sourcePixelBytes =
+ gl::GetSizedInternalFormatInfo(sourceFormat.fboImplementationInternalFormat).pixelBytes;
+
+ GLenum destUnsizedFormat = gl::GetUnsizedFormat(dest->getInternalFormat());
+ const auto &destFormat = d3d11::Format::Get(dest->getInternalFormat(), rendererCaps).format();
+ const auto &destFormatInfo =
+ gl::GetSizedInternalFormatInfo(destFormat.fboImplementationInternalFormat);
+ GLuint destPixelBytes = destFormatInfo.pixelBytes;
- dxgiFormatInfo.mipGenerationFunction(src->getWidth(), src->getHeight(), src->getDepth(),
- sourceData, srcMapped.RowPitch, srcMapped.DepthPitch,
- destData, destMapped.RowPitch, destMapped.DepthPitch);
+ const uint8_t *sourceData = reinterpret_cast<const uint8_t *>(srcMapped.pData) +
+ sourceRect.x * sourcePixelBytes + sourceRect.y * srcMapped.RowPitch;
+ uint8_t *destData = reinterpret_cast<uint8_t *>(destMapped.pData) +
+ destOffset.x * destPixelBytes + destOffset.y * destMapped.RowPitch;
+
+ CopyImageCHROMIUM(sourceData, srcMapped.RowPitch, sourcePixelBytes,
+ sourceFormat.colorReadFunction, destData, destMapped.RowPitch, destPixelBytes,
+ destFormat.colorWriteFunction, destUnsizedFormat,
+ destFormatInfo.componentType, sourceRect.width, sourceRect.height,
+ unpackFlipY, unpackPremultiplyAlpha, unpackUnmultiplyAlpha);
dest->unmap();
- src->unmap();
+ source->unmap();
dest->markDirty();
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
bool Image11::isDirty() const
{
- // If mDirty is true
- // AND mStagingTexture doesn't exist AND mStagingTexture doesn't need to be recovered from TextureStorage
- // AND the texture doesn't require init data (i.e. a blank new texture will suffice)
- // then isDirty should still return false.
- if (mDirty && !mStagingTexture && !mRecoverFromStorage)
+ // If mDirty is true AND mStagingTexture doesn't exist AND mStagingTexture doesn't need to be
+ // recovered from TextureStorage AND the texture doesn't require init data (i.e. a blank new
+ // texture will suffice) AND robust resource initialization is not enabled then isDirty should
+ // still return false.
+ if (mDirty && !mStagingTexture.valid() && !mRecoverFromStorage)
{
const Renderer11DeviceCaps &deviceCaps = mRenderer->getRenderer11DeviceCaps();
- const d3d11::TextureFormat formatInfo = d3d11::GetTextureFormatInfo(mInternalFormat, deviceCaps);
+ const auto &formatInfo = d3d11::Format::Get(mInternalFormat, deviceCaps);
if (formatInfo.dataInitializerFunction == nullptr)
{
return false;
@@ -99,92 +150,69 @@ bool Image11::isDirty() const
return mDirty;
}
-gl::Error Image11::copyToStorage(TextureStorage *storage, const gl::ImageIndex &index, const gl::Box &region)
+gl::Error Image11::copyToStorage(const gl::Context *context,
+ TextureStorage *storage,
+ const gl::ImageIndex &index,
+ const gl::Box &region)
{
TextureStorage11 *storage11 = GetAs<TextureStorage11>(storage);
- // If an app's behavior results in an Image11 copying its data to/from to a TextureStorage multiple times,
- // then we should just keep the staging texture around to prevent the copying from impacting perf.
- // We allow the Image11 to copy its data to/from TextureStorage once.
- // This accounts for an app making a late call to glGenerateMipmap.
+ // If an app's behavior results in an Image11 copying its data to/from to a TextureStorage
+ // multiple times, then we should just keep the staging texture around to prevent the copying
+ // from impacting perf. We allow the Image11 to copy its data to/from TextureStorage once. This
+ // accounts for an app making a late call to glGenerateMipmap.
bool attemptToReleaseStagingTexture = (mRecoveredFromStorageCount < 2);
if (attemptToReleaseStagingTexture)
{
- // If another image is relying on this Storage for its data, then we must let it recover its data before we overwrite it.
- gl::Error error = storage11->releaseAssociatedImage(index, this);
- if (error.isError())
- {
- return error;
- }
+ // If another image is relying on this Storage for its data, then we must let it recover its
+ // data before we overwrite it.
+ ANGLE_TRY(storage11->releaseAssociatedImage(context, index, this));
}
- ID3D11Resource *stagingTexture = NULL;
+ const TextureHelper11 *stagingTexture = nullptr;
unsigned int stagingSubresourceIndex = 0;
- gl::Error error = getStagingTexture(&stagingTexture, &stagingSubresourceIndex);
- if (error.isError())
- {
- return error;
- }
-
- error = storage11->updateSubresourceLevel(stagingTexture, stagingSubresourceIndex, index, region);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(getStagingTexture(&stagingTexture, &stagingSubresourceIndex));
+ ANGLE_TRY(storage11->updateSubresourceLevel(context, *stagingTexture, stagingSubresourceIndex,
+ index, region));
// Once the image data has been copied into the Storage, we can release it locally.
if (attemptToReleaseStagingTexture)
{
storage11->associateImage(this, index);
releaseStagingTexture();
- mRecoverFromStorage = true;
- mAssociatedStorage = storage11;
+ mRecoverFromStorage = true;
+ mAssociatedStorage = storage11;
mAssociatedImageIndex = index;
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-bool Image11::isAssociatedStorageValid(TextureStorage11* textureStorage) const
+void Image11::verifyAssociatedStorageValid(TextureStorage11 *textureStorage) const
{
- return (mAssociatedStorage == textureStorage);
+ ASSERT(mAssociatedStorage == textureStorage);
}
-gl::Error Image11::recoverFromAssociatedStorage()
+gl::Error Image11::recoverFromAssociatedStorage(const gl::Context *context)
{
if (mRecoverFromStorage)
{
- gl::Error error = createStagingTexture();
- if (error.isError())
- {
- return error;
- }
-
- bool textureStorageCorrect = mAssociatedStorage->isAssociatedImageValid(mAssociatedImageIndex, this);
+ ANGLE_TRY(createStagingTexture());
- // This means that the cached TextureStorage has been modified after this Image11 released its copy of its data.
- // This should not have happened. The TextureStorage should have told this Image11 to recover its data before it was overwritten.
- ASSERT(textureStorageCorrect);
+ mAssociatedStorage->verifyAssociatedImageValid(mAssociatedImageIndex, this);
- if (textureStorageCorrect)
- {
- // CopySubResource from the Storage to the Staging texture
- gl::Box region(0, 0, 0, mWidth, mHeight, mDepth);
- error = mAssociatedStorage->copySubresourceLevel(mStagingTexture, mStagingSubresource, mAssociatedImageIndex, region);
- if (error.isError())
- {
- return error;
- }
-
- mRecoveredFromStorageCount += 1;
- }
+ // CopySubResource from the Storage to the Staging texture
+ gl::Box region(0, 0, 0, mWidth, mHeight, mDepth);
+ ANGLE_TRY(mAssociatedStorage->copySubresourceLevel(
+ context, mStagingTexture, mStagingSubresource, mAssociatedImageIndex, region));
+ mRecoveredFromStorageCount += 1;
// Reset all the recovery parameters, even if the texture storage association is broken.
disassociateStorage();
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
void Image11::disassociateStorage()
@@ -194,17 +222,18 @@ void Image11::disassociateStorage()
// Make the texturestorage release the Image11 too
mAssociatedStorage->disassociateImage(mAssociatedImageIndex, this);
- mRecoverFromStorage = false;
- mAssociatedStorage = NULL;
+ mRecoverFromStorage = false;
+ mAssociatedStorage = nullptr;
mAssociatedImageIndex = gl::ImageIndex::MakeInvalid();
}
}
-bool Image11::redefine(GLenum target, GLenum internalformat, const gl::Extents &size, bool forceRelease)
+bool Image11::redefine(GLenum target,
+ GLenum internalformat,
+ const gl::Extents &size,
+ bool forceRelease)
{
- if (mWidth != size.width ||
- mHeight != size.height ||
- mInternalFormat != internalformat ||
+ if (mWidth != size.width || mHeight != size.height || mInternalFormat != internalformat ||
forceRelease)
{
// End the association with the TextureStorage, since that data will be out of date.
@@ -212,19 +241,20 @@ bool Image11::redefine(GLenum target, GLenum internalformat, const gl::Extents &
disassociateStorage();
mRecoveredFromStorageCount = 0;
- mWidth = size.width;
- mHeight = size.height;
- mDepth = size.depth;
+ mWidth = size.width;
+ mHeight = size.height;
+ mDepth = size.depth;
mInternalFormat = internalformat;
- mTarget = target;
+ mTarget = target;
// compute the d3d format that will be used
- const d3d11::TextureFormat &formatInfo = d3d11::GetTextureFormatInfo(internalformat, mRenderer->getRenderer11DeviceCaps());
+ const d3d11::Format &formatInfo =
+ d3d11::Format::Get(internalformat, mRenderer->getRenderer11DeviceCaps());
mDXGIFormat = formatInfo.texFormat;
mRenderable = (formatInfo.rtvFormat != DXGI_FORMAT_UNKNOWN);
releaseStagingTexture();
- mDirty = (formatInfo.dataInitializerFunction != NULL);
+ mDirty = (formatInfo.dataInitializerFunction != nullptr);
return true;
}
@@ -241,119 +271,125 @@ DXGI_FORMAT Image11::getDXGIFormat() const
return mDXGIFormat;
}
-// Store the pixel rectangle designated by xoffset,yoffset,width,height with pixels stored as format/type at input
+// Store the pixel rectangle designated by xoffset,yoffset,width,height with pixels stored as
+// format/type at input
// into the target pixel rectangle.
-gl::Error Image11::loadData(const gl::Box &area, const gl::PixelUnpackState &unpack, GLenum type, const void *input)
+gl::Error Image11::loadData(const gl::Context *context,
+ const gl::Box &area,
+ const gl::PixelUnpackState &unpack,
+ GLenum type,
+ const void *input,
+ bool applySkipImages)
{
- const gl::InternalFormat &formatInfo = gl::GetInternalFormatInfo(mInternalFormat);
- GLsizei inputRowPitch = formatInfo.computeRowPitch(type, area.width, unpack.alignment, unpack.rowLength);
- GLsizei inputDepthPitch = formatInfo.computeDepthPitch(
- type, area.width, area.height, unpack.alignment, unpack.rowLength, unpack.imageHeight);
- GLsizei inputSkipBytes = formatInfo.computeSkipPixels(
- inputRowPitch, inputDepthPitch, unpack.skipImages, unpack.skipRows, unpack.skipPixels);
-
- const d3d11::DXGIFormat &dxgiFormatInfo = d3d11::GetDXGIFormatInfo(mDXGIFormat);
- GLuint outputPixelSize = dxgiFormatInfo.pixelBytes;
-
- const d3d11::TextureFormat &d3dFormatInfo = d3d11::GetTextureFormatInfo(mInternalFormat, mRenderer->getRenderer11DeviceCaps());
- LoadImageFunction loadFunction = d3dFormatInfo.loadFunctions.at(type).loadFunction;
+ const gl::InternalFormat &formatInfo = gl::GetSizedInternalFormatInfo(mInternalFormat);
+ GLuint inputRowPitch = 0;
+ ANGLE_TRY_RESULT(
+ formatInfo.computeRowPitch(type, area.width, unpack.alignment, unpack.rowLength),
+ inputRowPitch);
+ GLuint inputDepthPitch = 0;
+ ANGLE_TRY_RESULT(formatInfo.computeDepthPitch(area.height, unpack.imageHeight, inputRowPitch),
+ inputDepthPitch);
+ GLuint inputSkipBytes = 0;
+ ANGLE_TRY_RESULT(
+ formatInfo.computeSkipBytes(inputRowPitch, inputDepthPitch, unpack, applySkipImages),
+ inputSkipBytes);
+
+ const d3d11::DXGIFormatSize &dxgiFormatInfo = d3d11::GetDXGIFormatSizeInfo(mDXGIFormat);
+ GLuint outputPixelSize = dxgiFormatInfo.pixelBytes;
+
+ const d3d11::Format &d3dFormatInfo =
+ d3d11::Format::Get(mInternalFormat, mRenderer->getRenderer11DeviceCaps());
+ LoadImageFunction loadFunction = d3dFormatInfo.getLoadFunctions()(type).loadFunction;
D3D11_MAPPED_SUBRESOURCE mappedImage;
- gl::Error error = map(D3D11_MAP_WRITE, &mappedImage);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(map(context, D3D11_MAP_WRITE, &mappedImage));
- uint8_t *offsetMappedData = (reinterpret_cast<uint8_t*>(mappedImage.pData) + (area.y * mappedImage.RowPitch + area.x * outputPixelSize + area.z * mappedImage.DepthPitch));
+ uint8_t *offsetMappedData = (reinterpret_cast<uint8_t *>(mappedImage.pData) +
+ (area.y * mappedImage.RowPitch + area.x * outputPixelSize +
+ area.z * mappedImage.DepthPitch));
loadFunction(area.width, area.height, area.depth,
reinterpret_cast<const uint8_t *>(input) + inputSkipBytes, inputRowPitch,
inputDepthPitch, offsetMappedData, mappedImage.RowPitch, mappedImage.DepthPitch);
unmap();
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error Image11::loadCompressedData(const gl::Box &area, const void *input)
+gl::Error Image11::loadCompressedData(const gl::Context *context,
+ const gl::Box &area,
+ const void *input)
{
- const gl::InternalFormat &formatInfo = gl::GetInternalFormatInfo(mInternalFormat);
- GLsizei inputRowPitch = formatInfo.computeRowPitch(GL_UNSIGNED_BYTE, area.width, 1, 0);
- GLsizei inputDepthPitch =
- formatInfo.computeDepthPitch(GL_UNSIGNED_BYTE, area.width, area.height, 1, 0, 0);
+ const gl::InternalFormat &formatInfo = gl::GetSizedInternalFormatInfo(mInternalFormat);
+ GLsizei inputRowPitch = 0;
+ ANGLE_TRY_RESULT(formatInfo.computeRowPitch(GL_UNSIGNED_BYTE, area.width, 1, 0), inputRowPitch);
+ GLsizei inputDepthPitch = 0;
+ ANGLE_TRY_RESULT(formatInfo.computeDepthPitch(area.height, 0, inputRowPitch), inputDepthPitch);
- const d3d11::DXGIFormat &dxgiFormatInfo = d3d11::GetDXGIFormatInfo(mDXGIFormat);
- GLuint outputPixelSize = dxgiFormatInfo.pixelBytes;
- GLuint outputBlockWidth = dxgiFormatInfo.blockWidth;
- GLuint outputBlockHeight = dxgiFormatInfo.blockHeight;
+ const d3d11::DXGIFormatSize &dxgiFormatInfo = d3d11::GetDXGIFormatSizeInfo(mDXGIFormat);
+ GLuint outputPixelSize = dxgiFormatInfo.pixelBytes;
+ GLuint outputBlockWidth = dxgiFormatInfo.blockWidth;
+ GLuint outputBlockHeight = dxgiFormatInfo.blockHeight;
ASSERT(area.x % outputBlockWidth == 0);
ASSERT(area.y % outputBlockHeight == 0);
- const d3d11::TextureFormat &d3dFormatInfo = d3d11::GetTextureFormatInfo(mInternalFormat, mRenderer->getRenderer11DeviceCaps());
- LoadImageFunction loadFunction = d3dFormatInfo.loadFunctions.at(GL_UNSIGNED_BYTE).loadFunction;
+ const d3d11::Format &d3dFormatInfo =
+ d3d11::Format::Get(mInternalFormat, mRenderer->getRenderer11DeviceCaps());
+ LoadImageFunction loadFunction =
+ d3dFormatInfo.getLoadFunctions()(GL_UNSIGNED_BYTE).loadFunction;
D3D11_MAPPED_SUBRESOURCE mappedImage;
- gl::Error error = map(D3D11_MAP_WRITE, &mappedImage);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(map(context, D3D11_MAP_WRITE, &mappedImage));
- uint8_t* offsetMappedData = reinterpret_cast<uint8_t*>(mappedImage.pData) + ((area.y / outputBlockHeight) * mappedImage.RowPitch +
- (area.x / outputBlockWidth) * outputPixelSize +
- area.z * mappedImage.DepthPitch);
+ uint8_t *offsetMappedData =
+ reinterpret_cast<uint8_t *>(mappedImage.pData) +
+ ((area.y / outputBlockHeight) * mappedImage.RowPitch +
+ (area.x / outputBlockWidth) * outputPixelSize + area.z * mappedImage.DepthPitch);
- loadFunction(area.width, area.height, area.depth,
- reinterpret_cast<const uint8_t*>(input), inputRowPitch, inputDepthPitch,
- offsetMappedData, mappedImage.RowPitch, mappedImage.DepthPitch);
+ loadFunction(area.width, area.height, area.depth, reinterpret_cast<const uint8_t *>(input),
+ inputRowPitch, inputDepthPitch, offsetMappedData, mappedImage.RowPitch,
+ mappedImage.DepthPitch);
unmap();
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error Image11::copyFromTexStorage(const gl::ImageIndex &imageIndex, TextureStorage *source)
+gl::Error Image11::copyFromTexStorage(const gl::Context *context,
+ const gl::ImageIndex &imageIndex,
+ TextureStorage *source)
{
TextureStorage11 *storage11 = GetAs<TextureStorage11>(source);
- ID3D11Resource *resource = nullptr;
- gl::Error error = storage11->getResource(&resource);
- if (error.isError())
- {
- return error;
- }
+ const TextureHelper11 *textureHelper = nullptr;
+ ANGLE_TRY(storage11->getResource(context, &textureHelper));
- UINT subresourceIndex = storage11->getSubresourceIndex(imageIndex);
- TextureHelper11 textureHelper = TextureHelper11::MakeAndReference(resource);
+ UINT subresourceIndex = storage11->getSubresourceIndex(imageIndex);
gl::Box sourceBox(0, 0, 0, mWidth, mHeight, mDepth);
- return copyWithoutConversion(gl::Offset(), sourceBox, textureHelper, subresourceIndex);
+ return copyWithoutConversion(gl::Offset(), sourceBox, *textureHelper, subresourceIndex);
}
-gl::Error Image11::copyFromFramebuffer(const gl::Offset &destOffset,
+gl::Error Image11::copyFromFramebuffer(const gl::Context *context,
+ const gl::Offset &destOffset,
const gl::Rectangle &sourceArea,
const gl::Framebuffer *sourceFBO)
{
const gl::FramebufferAttachment *srcAttachment = sourceFBO->getReadColorbuffer();
ASSERT(srcAttachment);
- const auto &d3d11Format = d3d11::GetTextureFormatInfo(srcAttachment->getInternalFormat(),
- mRenderer->getRenderer11DeviceCaps());
+ GLenum sourceInternalFormat = srcAttachment->getFormat().info->sizedInternalFormat;
+ const auto &d3d11Format =
+ d3d11::Format::Get(sourceInternalFormat, mRenderer->getRenderer11DeviceCaps());
- if (d3d11Format.texFormat == mDXGIFormat)
+ if (d3d11Format.texFormat == mDXGIFormat && sourceInternalFormat == mInternalFormat)
{
- RenderTargetD3D *renderTarget = nullptr;
- gl::Error error = srcAttachment->getRenderTarget(&renderTarget);
- if (error.isError())
- {
- return error;
- }
-
- RenderTarget11 *rt11 = GetAs<RenderTarget11>(renderTarget);
- ASSERT(rt11->getTexture());
+ RenderTarget11 *rt11 = nullptr;
+ ANGLE_TRY(srcAttachment->getRenderTarget(context, &rt11));
+ ASSERT(rt11->getTexture().get());
- TextureHelper11 textureHelper = TextureHelper11::MakeAndReference(rt11->getTexture());
+ TextureHelper11 textureHelper = rt11->getTexture();
unsigned int sourceSubResource = rt11->getSubresourceIndex();
gl::Box sourceBox(sourceArea.x, sourceArea.y, 0, sourceArea.width, sourceArea.height, 1);
@@ -363,25 +399,47 @@ gl::Error Image11::copyFromFramebuffer(const gl::Offset &destOffset,
// This format requires conversion, so we must copy the texture to staging and manually convert
// via readPixels
D3D11_MAPPED_SUBRESOURCE mappedImage;
- gl::Error error = map(D3D11_MAP_WRITE, &mappedImage);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(map(context, D3D11_MAP_WRITE, &mappedImage));
// determine the offset coordinate into the destination buffer
- const auto &dxgiFormatInfo = d3d11::GetDXGIFormatInfo(mDXGIFormat);
+ const auto &dxgiFormatInfo = d3d11::GetDXGIFormatSizeInfo(mDXGIFormat);
GLsizei rowOffset = dxgiFormatInfo.pixelBytes * destOffset.x;
uint8_t *dataOffset = static_cast<uint8_t *>(mappedImage.pData) +
mappedImage.RowPitch * destOffset.y + rowOffset +
destOffset.z * mappedImage.DepthPitch;
- const gl::InternalFormat &formatInfo = gl::GetInternalFormatInfo(mInternalFormat);
+ const gl::InternalFormat &destFormatInfo = gl::GetSizedInternalFormatInfo(mInternalFormat);
+ const auto &destD3D11Format =
+ d3d11::Format::Get(mInternalFormat, mRenderer->getRenderer11DeviceCaps());
+
+ auto loadFunction = destD3D11Format.getLoadFunctions()(destFormatInfo.type);
+ gl::Error error = gl::NoError();
+ if (loadFunction.requiresConversion)
+ {
+ size_t bufferSize = destFormatInfo.pixelBytes * sourceArea.width * sourceArea.height;
+ angle::MemoryBuffer *memoryBuffer = nullptr;
+ error = mRenderer->getScratchMemoryBuffer(bufferSize, &memoryBuffer);
+
+ if (!error.isError())
+ {
+ GLuint memoryBufferRowPitch = destFormatInfo.pixelBytes * sourceArea.width;
- error = mRenderer->readFromAttachment(*srcAttachment, sourceArea, formatInfo.format,
- formatInfo.type, mappedImage.RowPitch,
- gl::PixelPackState(), dataOffset);
+ error = mRenderer->readFromAttachment(
+ context, *srcAttachment, sourceArea, destFormatInfo.format, destFormatInfo.type,
+ memoryBufferRowPitch, gl::PixelPackState(), memoryBuffer->data());
+
+ loadFunction.loadFunction(sourceArea.width, sourceArea.height, 1, memoryBuffer->data(),
+ memoryBufferRowPitch, 0, dataOffset, mappedImage.RowPitch,
+ mappedImage.DepthPitch);
+ }
+ }
+ else
+ {
+ error = mRenderer->readFromAttachment(
+ context, *srcAttachment, sourceArea, destFormatInfo.format, destFormatInfo.type,
+ mappedImage.RowPitch, gl::PixelPackState(), dataOffset);
+ }
unmap();
mDirty = true;
@@ -395,26 +453,23 @@ gl::Error Image11::copyWithoutConversion(const gl::Offset &destOffset,
UINT sourceSubResource)
{
// No conversion needed-- use copyback fastpath
- ID3D11Resource *stagingTexture = nullptr;
+ const TextureHelper11 *stagingTexture = nullptr;
unsigned int stagingSubresourceIndex = 0;
- gl::Error error = getStagingTexture(&stagingTexture, &stagingSubresourceIndex);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(getStagingTexture(&stagingTexture, &stagingSubresourceIndex));
- ID3D11Device *device = mRenderer->getDevice();
ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
- UINT subresourceAfterResolve = sourceSubResource;
-
- ID3D11Resource *srcTex = nullptr;
const gl::Extents &extents = textureHelper.getExtents();
- bool needResolve =
- (textureHelper.getTextureType() == GL_TEXTURE_2D && textureHelper.getSampleCount() > 1);
+ D3D11_BOX srcBox;
+ srcBox.left = sourceArea.x;
+ srcBox.right = sourceArea.x + sourceArea.width;
+ srcBox.top = sourceArea.y;
+ srcBox.bottom = sourceArea.y + sourceArea.height;
+ srcBox.front = sourceArea.z;
+ srcBox.back = sourceArea.z + sourceArea.depth;
- if (needResolve)
+ if (textureHelper.is2D() && textureHelper.getSampleCount() > 1)
{
D3D11_TEXTURE2D_DESC resolveDesc;
resolveDesc.Width = extents.width;
@@ -429,80 +484,57 @@ gl::Error Image11::copyWithoutConversion(const gl::Offset &destOffset,
resolveDesc.CPUAccessFlags = 0;
resolveDesc.MiscFlags = 0;
- ID3D11Texture2D *srcTex2D = NULL;
- HRESULT result = device->CreateTexture2D(&resolveDesc, NULL, &srcTex2D);
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY,
- "Failed to create resolve texture for Image11::copy, HRESULT: 0x%X.",
- result);
- }
- srcTex = srcTex2D;
+ d3d11::Texture2D resolveTex;
+ ANGLE_TRY(mRenderer->allocateResource(resolveDesc, &resolveTex));
- deviceContext->ResolveSubresource(srcTex, 0, textureHelper.getTexture2D(),
+ deviceContext->ResolveSubresource(resolveTex.get(), 0, textureHelper.get(),
sourceSubResource, textureHelper.getFormat());
- subresourceAfterResolve = 0;
+
+ deviceContext->CopySubresourceRegion(stagingTexture->get(), stagingSubresourceIndex,
+ destOffset.x, destOffset.y, destOffset.z,
+ resolveTex.get(), 0, &srcBox);
}
else
{
- srcTex = textureHelper.getResource();
- }
-
- D3D11_BOX srcBox;
- srcBox.left = sourceArea.x;
- srcBox.right = sourceArea.x + sourceArea.width;
- srcBox.top = sourceArea.y;
- srcBox.bottom = sourceArea.y + sourceArea.height;
- srcBox.front = sourceArea.z;
- srcBox.back = sourceArea.z + sourceArea.depth;
-
- deviceContext->CopySubresourceRegion(stagingTexture, stagingSubresourceIndex, destOffset.x,
- destOffset.y, destOffset.z, srcTex,
- subresourceAfterResolve, &srcBox);
-
- if (needResolve)
- {
- SafeRelease(srcTex);
+ deviceContext->CopySubresourceRegion(stagingTexture->get(), stagingSubresourceIndex,
+ destOffset.x, destOffset.y, destOffset.z,
+ textureHelper.get(), sourceSubResource, &srcBox);
}
mDirty = true;
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error Image11::getStagingTexture(ID3D11Resource **outStagingTexture, unsigned int *outSubresourceIndex)
+gl::Error Image11::getStagingTexture(const TextureHelper11 **outStagingTexture,
+ unsigned int *outSubresourceIndex)
{
- gl::Error error = createStagingTexture();
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(createStagingTexture());
- *outStagingTexture = mStagingTexture;
+ *outStagingTexture = &mStagingTexture;
*outSubresourceIndex = mStagingSubresource;
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
void Image11::releaseStagingTexture()
{
- SafeRelease(mStagingTexture);
+ mStagingTexture.reset();
}
gl::Error Image11::createStagingTexture()
{
- if (mStagingTexture)
+ if (mStagingTexture.valid())
{
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
ASSERT(mWidth > 0 && mHeight > 0 && mDepth > 0);
const DXGI_FORMAT dxgiFormat = getDXGIFormat();
+ const auto &formatInfo =
+ d3d11::Format::Get(mInternalFormat, mRenderer->getRenderer11DeviceCaps());
- ID3D11Device *device = mRenderer->getDevice();
- HRESULT result;
-
- int lodOffset = 1;
- GLsizei width = mWidth;
+ int lodOffset = 1;
+ GLsizei width = mWidth;
GLsizei height = mHeight;
// adjust size if needed for compressed textures
@@ -510,80 +542,69 @@ gl::Error Image11::createStagingTexture()
if (mTarget == GL_TEXTURE_3D)
{
- ID3D11Texture3D *newTexture = NULL;
-
D3D11_TEXTURE3D_DESC desc;
- desc.Width = width;
- desc.Height = height;
- desc.Depth = mDepth;
- desc.MipLevels = lodOffset + 1;
- desc.Format = dxgiFormat;
- desc.Usage = D3D11_USAGE_STAGING;
- desc.BindFlags = 0;
+ desc.Width = width;
+ desc.Height = height;
+ desc.Depth = mDepth;
+ desc.MipLevels = lodOffset + 1;
+ desc.Format = dxgiFormat;
+ desc.Usage = D3D11_USAGE_STAGING;
+ desc.BindFlags = 0;
desc.CPUAccessFlags = D3D11_CPU_ACCESS_READ | D3D11_CPU_ACCESS_WRITE;
- desc.MiscFlags = 0;
+ desc.MiscFlags = 0;
- if (d3d11::GetTextureFormatInfo(mInternalFormat, mRenderer->getRenderer11DeviceCaps()).dataInitializerFunction != NULL)
+ if (formatInfo.dataInitializerFunction != nullptr)
{
std::vector<D3D11_SUBRESOURCE_DATA> initialData;
std::vector<std::vector<BYTE>> textureData;
- d3d11::GenerateInitialTextureData(mInternalFormat, mRenderer->getRenderer11DeviceCaps(), width, height, mDepth,
- lodOffset + 1, &initialData, &textureData);
+ d3d11::GenerateInitialTextureData(mInternalFormat, mRenderer->getRenderer11DeviceCaps(),
+ width, height, mDepth, lodOffset + 1, &initialData,
+ &textureData);
- result = device->CreateTexture3D(&desc, initialData.data(), &newTexture);
+ ANGLE_TRY(
+ mRenderer->allocateTexture(desc, formatInfo, initialData.data(), &mStagingTexture));
}
else
{
- result = device->CreateTexture3D(&desc, NULL, &newTexture);
+ ANGLE_TRY(mRenderer->allocateTexture(desc, formatInfo, &mStagingTexture));
}
- if (FAILED(result))
- {
- ASSERT(result == E_OUTOFMEMORY);
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create staging texture, result: 0x%X.", result);
- }
-
- mStagingTexture = newTexture;
+ mStagingTexture.setDebugName("Image11::StagingTexture3D");
mStagingSubresource = D3D11CalcSubresource(lodOffset, 0, lodOffset + 1);
}
- else if (mTarget == GL_TEXTURE_2D || mTarget == GL_TEXTURE_2D_ARRAY || mTarget == GL_TEXTURE_CUBE_MAP)
+ else if (mTarget == GL_TEXTURE_2D || mTarget == GL_TEXTURE_2D_ARRAY ||
+ mTarget == GL_TEXTURE_CUBE_MAP)
{
- ID3D11Texture2D *newTexture = NULL;
-
D3D11_TEXTURE2D_DESC desc;
- desc.Width = width;
- desc.Height = height;
- desc.MipLevels = lodOffset + 1;
- desc.ArraySize = 1;
- desc.Format = dxgiFormat;
- desc.SampleDesc.Count = 1;
+ desc.Width = width;
+ desc.Height = height;
+ desc.MipLevels = lodOffset + 1;
+ desc.ArraySize = 1;
+ desc.Format = dxgiFormat;
+ desc.SampleDesc.Count = 1;
desc.SampleDesc.Quality = 0;
- desc.Usage = D3D11_USAGE_STAGING;
- desc.BindFlags = 0;
- desc.CPUAccessFlags = D3D11_CPU_ACCESS_READ | D3D11_CPU_ACCESS_WRITE;
- desc.MiscFlags = 0;
+ desc.Usage = D3D11_USAGE_STAGING;
+ desc.BindFlags = 0;
+ desc.CPUAccessFlags = D3D11_CPU_ACCESS_READ | D3D11_CPU_ACCESS_WRITE;
+ desc.MiscFlags = 0;
- if (d3d11::GetTextureFormatInfo(mInternalFormat, mRenderer->getRenderer11DeviceCaps()).dataInitializerFunction != NULL)
+ if (formatInfo.dataInitializerFunction != nullptr)
{
std::vector<D3D11_SUBRESOURCE_DATA> initialData;
std::vector<std::vector<BYTE>> textureData;
- d3d11::GenerateInitialTextureData(mInternalFormat, mRenderer->getRenderer11DeviceCaps(), width, height, 1,
- lodOffset + 1, &initialData, &textureData);
+ d3d11::GenerateInitialTextureData(mInternalFormat, mRenderer->getRenderer11DeviceCaps(),
+ width, height, 1, lodOffset + 1, &initialData,
+ &textureData);
- result = device->CreateTexture2D(&desc, initialData.data(), &newTexture);
+ ANGLE_TRY(
+ mRenderer->allocateTexture(desc, formatInfo, initialData.data(), &mStagingTexture));
}
else
{
- result = device->CreateTexture2D(&desc, NULL, &newTexture);
+ ANGLE_TRY(mRenderer->allocateTexture(desc, formatInfo, &mStagingTexture));
}
- if (FAILED(result))
- {
- ASSERT(result == E_OUTOFMEMORY);
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create staging texture, result: 0x%X.", result);
- }
-
- mStagingTexture = newTexture;
+ mStagingTexture.setDebugName("Image11::StagingTexture2D");
mStagingSubresource = D3D11CalcSubresource(lodOffset, 0, lodOffset + 1);
}
else
@@ -592,30 +613,22 @@ gl::Error Image11::createStagingTexture()
}
mDirty = false;
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error Image11::map(D3D11_MAP mapType, D3D11_MAPPED_SUBRESOURCE *map)
+gl::Error Image11::map(const gl::Context *context, D3D11_MAP mapType, D3D11_MAPPED_SUBRESOURCE *map)
{
// We must recover from the TextureStorage if necessary, even for D3D11_MAP_WRITE.
- gl::Error error = recoverFromAssociatedStorage();
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(recoverFromAssociatedStorage(context));
- ID3D11Resource *stagingTexture = NULL;
- unsigned int subresourceIndex = 0;
- error = getStagingTexture(&stagingTexture, &subresourceIndex);
- if (error.isError())
- {
- return error;
- }
+ const TextureHelper11 *stagingTexture = nullptr;
+ unsigned int subresourceIndex = 0;
+ ANGLE_TRY(getStagingTexture(&stagingTexture, &subresourceIndex));
ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
- ASSERT(mStagingTexture);
- HRESULT result = deviceContext->Map(stagingTexture, subresourceIndex, mapType, 0, map);
+ ASSERT(stagingTexture && stagingTexture->valid());
+ HRESULT result = deviceContext->Map(stagingTexture->get(), subresourceIndex, mapType, 0, map);
if (FAILED(result))
{
@@ -624,20 +637,20 @@ gl::Error Image11::map(D3D11_MAP mapType, D3D11_MAPPED_SUBRESOURCE *map)
{
mRenderer->notifyDeviceLost();
}
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to map staging texture, result: 0x%X.", result);
+ return gl::OutOfMemory() << "Failed to map staging texture, " << gl::FmtHR(result);
}
mDirty = true;
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
void Image11::unmap()
{
- if (mStagingTexture)
+ if (mStagingTexture.valid())
{
ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
- deviceContext->Unmap(mStagingTexture, mStagingSubresource);
+ deviceContext->Unmap(mStagingTexture.get(), mStagingSubresource);
}
}
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Image11.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Image11.h
index a5fcec84f8..584d231b37 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Image11.h
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Image11.h
@@ -10,10 +10,10 @@
#ifndef LIBANGLE_RENDERER_D3D_D3D11_IMAGE11_H_
#define LIBANGLE_RENDERER_D3D_D3D11_IMAGE11_H_
-#include "libANGLE/renderer/d3d/ImageD3D.h"
-#include "libANGLE/ImageIndex.h"
-
#include "common/debug.h"
+#include "libANGLE/ImageIndex.h"
+#include "libANGLE/renderer/d3d/ImageD3D.h"
+#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
namespace gl
{
@@ -25,37 +25,63 @@ namespace rx
class Renderer11;
class TextureHelper11;
class TextureStorage11;
+struct Renderer11DeviceCaps;
class Image11 : public ImageD3D
{
public:
Image11(Renderer11 *renderer);
- virtual ~Image11();
-
- static gl::Error generateMipmap(Image11 *dest, Image11 *src);
-
- virtual bool isDirty() const;
-
- virtual gl::Error copyToStorage(TextureStorage *storage, const gl::ImageIndex &index, const gl::Box &region);
+ ~Image11() override;
+
+ static gl::Error GenerateMipmap(const gl::Context *context,
+ Image11 *dest,
+ Image11 *src,
+ const Renderer11DeviceCaps &rendererCaps);
+ static gl::Error CopyImage(const gl::Context *context,
+ Image11 *dest,
+ Image11 *source,
+ const gl::Rectangle &sourceRect,
+ const gl::Offset &destOffset,
+ bool unpackFlipY,
+ bool unpackPremultiplyAlpha,
+ bool unpackUnmultiplyAlpha,
+ const Renderer11DeviceCaps &rendererCaps);
+
+ bool isDirty() const override;
+
+ gl::Error copyToStorage(const gl::Context *context,
+ TextureStorage *storage,
+ const gl::ImageIndex &index,
+ const gl::Box &region) override;
bool redefine(GLenum target, GLenum internalformat, const gl::Extents &size, bool forceRelease) override;
DXGI_FORMAT getDXGIFormat() const;
- virtual gl::Error loadData(const gl::Box &area, const gl::PixelUnpackState &unpack, GLenum type, const void *input);
- virtual gl::Error loadCompressedData(const gl::Box &area, const void *input);
-
- gl::Error copyFromTexStorage(const gl::ImageIndex &imageIndex, TextureStorage *source) override;
- gl::Error copyFromFramebuffer(const gl::Offset &destOffset,
+ gl::Error loadData(const gl::Context *context,
+ const gl::Box &area,
+ const gl::PixelUnpackState &unpack,
+ GLenum type,
+ const void *input,
+ bool applySkipImages) override;
+ gl::Error loadCompressedData(const gl::Context *context,
+ const gl::Box &area,
+ const void *input) override;
+
+ gl::Error copyFromTexStorage(const gl::Context *context,
+ const gl::ImageIndex &imageIndex,
+ TextureStorage *source) override;
+ gl::Error copyFromFramebuffer(const gl::Context *context,
+ const gl::Offset &destOffset,
const gl::Rectangle &sourceArea,
const gl::Framebuffer *source) override;
- gl::Error recoverFromAssociatedStorage();
- bool isAssociatedStorageValid(TextureStorage11* textureStorage) const;
+ gl::Error recoverFromAssociatedStorage(const gl::Context *context);
+ void verifyAssociatedStorageValid(TextureStorage11 *textureStorage) const;
void disassociateStorage();
protected:
- gl::Error map(D3D11_MAP mapType, D3D11_MAPPED_SUBRESOURCE *map);
+ gl::Error map(const gl::Context *context, D3D11_MAP mapType, D3D11_MAPPED_SUBRESOURCE *map);
void unmap();
private:
@@ -64,14 +90,15 @@ class Image11 : public ImageD3D
const TextureHelper11 &textureHelper,
UINT sourceSubResource);
- gl::Error getStagingTexture(ID3D11Resource **outStagingTexture, unsigned int *outSubresourceIndex);
+ gl::Error getStagingTexture(const TextureHelper11 **outStagingTexture,
+ unsigned int *outSubresourceIndex);
gl::Error createStagingTexture();
void releaseStagingTexture();
Renderer11 *mRenderer;
DXGI_FORMAT mDXGIFormat;
- ID3D11Resource *mStagingTexture;
+ TextureHelper11 mStagingTexture;
unsigned int mStagingSubresource;
bool mRecoverFromStorage;
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/IndexBuffer11.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/IndexBuffer11.cpp
index a5e78a245d..a79fb71f71 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/IndexBuffer11.cpp
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/IndexBuffer11.cpp
@@ -14,28 +14,23 @@
namespace rx
{
-IndexBuffer11::IndexBuffer11(Renderer11 *const renderer) : mRenderer(renderer)
+IndexBuffer11::IndexBuffer11(Renderer11 *const renderer)
+ : mRenderer(renderer), mBuffer(), mBufferSize(0), mIndexType(GL_NONE), mDynamicUsage(false)
{
- mBuffer = NULL;
- mBufferSize = 0;
- mDynamicUsage = false;
}
IndexBuffer11::~IndexBuffer11()
{
- SafeRelease(mBuffer);
}
gl::Error IndexBuffer11::initialize(unsigned int bufferSize, GLenum indexType, bool dynamic)
{
- SafeRelease(mBuffer);
+ mBuffer.reset();
updateSerial();
if (bufferSize > 0)
{
- ID3D11Device* dxDevice = mRenderer->getDevice();
-
D3D11_BUFFER_DESC bufferDesc;
bufferDesc.ByteWidth = bufferSize;
bufferDesc.Usage = D3D11_USAGE_DYNAMIC;
@@ -44,19 +39,15 @@ gl::Error IndexBuffer11::initialize(unsigned int bufferSize, GLenum indexType, b
bufferDesc.MiscFlags = 0;
bufferDesc.StructureByteStride = 0;
- HRESULT result = dxDevice->CreateBuffer(&bufferDesc, NULL, &mBuffer);
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to allocate internal index buffer of size, %lu.", bufferSize);
- }
+ ANGLE_TRY(mRenderer->allocateResource(bufferDesc, &mBuffer));
if (dynamic)
{
- d3d11::SetDebugName(mBuffer, "IndexBuffer11 (dynamic)");
+ mBuffer.setDebugName("IndexBuffer11 (dynamic)");
}
else
{
- d3d11::SetDebugName(mBuffer, "IndexBuffer11 (static)");
+ mBuffer.setDebugName("IndexBuffer11 (static)");
}
}
@@ -64,45 +55,46 @@ gl::Error IndexBuffer11::initialize(unsigned int bufferSize, GLenum indexType, b
mIndexType = indexType;
mDynamicUsage = dynamic;
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
gl::Error IndexBuffer11::mapBuffer(unsigned int offset, unsigned int size, void** outMappedMemory)
{
- if (!mBuffer)
+ if (!mBuffer.valid())
{
- return gl::Error(GL_OUT_OF_MEMORY, "Internal index buffer is not initialized.");
+ return gl::OutOfMemory() << "Internal index buffer is not initialized.";
}
// Check for integer overflows and out-out-bounds map requests
if (offset + size < offset || offset + size > mBufferSize)
{
- return gl::Error(GL_OUT_OF_MEMORY, "Index buffer map range is not inside the buffer.");
+ return gl::OutOfMemory() << "Index buffer map range is not inside the buffer.";
}
ID3D11DeviceContext *dxContext = mRenderer->getDeviceContext();
D3D11_MAPPED_SUBRESOURCE mappedResource;
- HRESULT result = dxContext->Map(mBuffer, 0, D3D11_MAP_WRITE_NO_OVERWRITE, 0, &mappedResource);
+ HRESULT result =
+ dxContext->Map(mBuffer.get(), 0, D3D11_MAP_WRITE_NO_OVERWRITE, 0, &mappedResource);
if (FAILED(result))
{
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to map internal index buffer, HRESULT: 0x%08x.", result);
+ return gl::OutOfMemory() << "Failed to map internal index buffer, " << gl::FmtHR(result);
}
*outMappedMemory = reinterpret_cast<char*>(mappedResource.pData) + offset;
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
gl::Error IndexBuffer11::unmapBuffer()
{
- if (!mBuffer)
+ if (!mBuffer.valid())
{
- return gl::Error(GL_OUT_OF_MEMORY, "Internal index buffer is not initialized.");
+ return gl::OutOfMemory() << "Internal index buffer is not initialized.";
}
ID3D11DeviceContext *dxContext = mRenderer->getDeviceContext();
- dxContext->Unmap(mBuffer, 0);
- return gl::Error(GL_NO_ERROR);
+ dxContext->Unmap(mBuffer.get(), 0);
+ return gl::NoError();
}
GLenum IndexBuffer11::getIndexType() const
@@ -123,29 +115,29 @@ gl::Error IndexBuffer11::setSize(unsigned int bufferSize, GLenum indexType)
}
else
{
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
}
gl::Error IndexBuffer11::discard()
{
- if (!mBuffer)
+ if (!mBuffer.valid())
{
- return gl::Error(GL_OUT_OF_MEMORY, "Internal index buffer is not initialized.");
+ return gl::OutOfMemory() << "Internal index buffer is not initialized.";
}
ID3D11DeviceContext *dxContext = mRenderer->getDeviceContext();
D3D11_MAPPED_SUBRESOURCE mappedResource;
- HRESULT result = dxContext->Map(mBuffer, 0, D3D11_MAP_WRITE_DISCARD, 0, &mappedResource);
+ HRESULT result = dxContext->Map(mBuffer.get(), 0, D3D11_MAP_WRITE_DISCARD, 0, &mappedResource);
if (FAILED(result))
{
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to map internal index buffer, HRESULT: 0x%08x.", result);
+ return gl::OutOfMemory() << "Failed to map internal index buffer, " << gl::FmtHR(result);
}
- dxContext->Unmap(mBuffer, 0);
+ dxContext->Unmap(mBuffer.get(), 0);
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
DXGI_FORMAT IndexBuffer11::getIndexFormat() const
@@ -159,9 +151,9 @@ DXGI_FORMAT IndexBuffer11::getIndexFormat() const
}
}
-ID3D11Buffer *IndexBuffer11::getBuffer() const
+const d3d11::Buffer &IndexBuffer11::getBuffer() const
{
return mBuffer;
}
-}
+} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/IndexBuffer11.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/IndexBuffer11.h
index e730377e00..7b5d744c02 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/IndexBuffer11.h
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/IndexBuffer11.h
@@ -10,6 +10,7 @@
#define LIBANGLE_RENDERER_D3D_D3D11_INDEXBUFFER11_H_
#include "libANGLE/renderer/d3d/IndexBuffer.h"
+#include "libANGLE/renderer/d3d/d3d11/ResourceManager11.h"
namespace rx
{
@@ -19,31 +20,31 @@ class IndexBuffer11 : public IndexBuffer
{
public:
explicit IndexBuffer11(Renderer11 *const renderer);
- virtual ~IndexBuffer11();
+ ~IndexBuffer11() override;
- virtual gl::Error initialize(unsigned int bufferSize, GLenum indexType, bool dynamic);
+ gl::Error initialize(unsigned int bufferSize, GLenum indexType, bool dynamic) override;
- virtual gl::Error mapBuffer(unsigned int offset, unsigned int size, void** outMappedMemory);
- virtual gl::Error unmapBuffer();
+ gl::Error mapBuffer(unsigned int offset, unsigned int size, void **outMappedMemory) override;
+ gl::Error unmapBuffer() override;
- virtual GLenum getIndexType() const;
- virtual unsigned int getBufferSize() const;
- virtual gl::Error setSize(unsigned int bufferSize, GLenum indexType);
+ GLenum getIndexType() const override;
+ unsigned int getBufferSize() const override;
+ gl::Error setSize(unsigned int bufferSize, GLenum indexType) override;
- virtual gl::Error discard();
+ gl::Error discard() override;
DXGI_FORMAT getIndexFormat() const;
- ID3D11Buffer *getBuffer() const;
+ const d3d11::Buffer &getBuffer() const;
private:
Renderer11 *const mRenderer;
- ID3D11Buffer *mBuffer;
+ d3d11::Buffer mBuffer;
unsigned int mBufferSize;
GLenum mIndexType;
bool mDynamicUsage;
};
-}
+} // namespace rx
#endif // LIBANGLE_RENDERER_D3D_D3D11_INDEXBUFFER11_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/InputLayoutCache.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/InputLayoutCache.cpp
index 3a6d797ea6..a238f97b08 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/InputLayoutCache.cpp
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/InputLayoutCache.cpp
@@ -9,17 +9,22 @@
#include "libANGLE/renderer/d3d/d3d11/InputLayoutCache.h"
+#include "common/bitset_utils.h"
#include "common/utilities.h"
+#include "libANGLE/Context.h"
#include "libANGLE/Program.h"
+#include "libANGLE/VertexArray.h"
#include "libANGLE/VertexAttribute.h"
#include "libANGLE/renderer/d3d/IndexDataManager.h"
#include "libANGLE/renderer/d3d/ProgramD3D.h"
#include "libANGLE/renderer/d3d/VertexDataManager.h"
#include "libANGLE/renderer/d3d/d3d11/Buffer11.h"
+#include "libANGLE/renderer/d3d/d3d11/Context11.h"
+#include "libANGLE/renderer/d3d/d3d11/Renderer11.h"
#include "libANGLE/renderer/d3d/d3d11/ShaderExecutable11.h"
+#include "libANGLE/renderer/d3d/d3d11/VertexArray11.h"
#include "libANGLE/renderer/d3d/d3d11/VertexBuffer11.h"
#include "libANGLE/renderer/d3d/d3d11/formatutils11.h"
-#include "third_party/murmurhash/MurmurHash3.h"
namespace rx
{
@@ -32,24 +37,7 @@ size_t GetReservedBufferCount(bool usesPointSpriteEmulation)
return usesPointSpriteEmulation ? 1 : 0;
}
-gl::InputLayout GetInputLayout(const SortedAttribArray &translatedAttributes, size_t attributeCount)
-{
- gl::InputLayout inputLayout(attributeCount, gl::VERTEX_FORMAT_INVALID);
-
- for (size_t attributeIndex = 0; attributeIndex < attributeCount; ++attributeIndex)
- {
- const TranslatedAttribute *translatedAttribute = translatedAttributes[attributeIndex];
-
- if (translatedAttribute->active)
- {
- inputLayout[attributeIndex] = gl::GetVertexFormatType(
- *translatedAttribute->attribute, translatedAttribute->currentValueType);
- }
- }
- return inputLayout;
-}
-
-GLenum GetGLSLAttributeType(const std::vector<sh::Attribute> &shaderAttributes, int index)
+GLenum GetGLSLAttributeType(const std::vector<sh::Attribute> &shaderAttributes, size_t index)
{
// Count matrices differently
for (const sh::Attribute &attrib : shaderAttributes)
@@ -61,8 +49,9 @@ GLenum GetGLSLAttributeType(const std::vector<sh::Attribute> &shaderAttributes,
GLenum transposedType = gl::TransposeMatrixType(attrib.type);
int rows = gl::VariableRowCount(transposedType);
+ int intIndex = static_cast<int>(index);
- if (index >= attrib.location && index < attrib.location + rows)
+ if (intIndex >= attrib.location && intIndex < attrib.location + rows)
{
return transposedType;
}
@@ -72,8 +61,6 @@ GLenum GetGLSLAttributeType(const std::vector<sh::Attribute> &shaderAttributes,
return GL_NONE;
}
-const unsigned int kDefaultCacheSize = 1024;
-
struct PackedAttribute
{
uint8_t attribType;
@@ -82,26 +69,18 @@ struct PackedAttribute
uint8_t divisor;
};
-Optional<size_t> FindFirstNonInstanced(const SortedAttribArray &sortedAttributes, size_t maxIndex)
-{
- for (size_t index = 0; index < maxIndex; ++index)
- {
- if (sortedAttributes[index]->divisor == 0)
- {
- return Optional<size_t>(index);
- }
- }
+} // anonymous namespace
- return Optional<size_t>::Invalid();
+PackedAttributeLayout::PackedAttributeLayout() : numAttributes(0), flags(0), attributeData({})
+{
}
-} // anonymous namespace
+PackedAttributeLayout::PackedAttributeLayout(const PackedAttributeLayout &other) = default;
-void InputLayoutCache::PackedAttributeLayout::addAttributeData(
- GLenum glType,
- UINT semanticIndex,
- gl::VertexFormatType vertexFormatType,
- unsigned int divisor)
+void PackedAttributeLayout::addAttributeData(GLenum glType,
+ UINT semanticIndex,
+ gl::VertexFormatType vertexFormatType,
+ unsigned int divisor)
{
gl::AttributeType attribType = gl::GetAttributeType(glType);
@@ -121,139 +100,58 @@ void InputLayoutCache::PackedAttributeLayout::addAttributeData(
attributeData[numAttributes++] = gl::bitCast<uint32_t>(packedAttrib);
}
-bool InputLayoutCache::PackedAttributeLayout::operator<(const PackedAttributeLayout &other) const
+bool PackedAttributeLayout::operator==(const PackedAttributeLayout &other) const
{
- if (numAttributes != other.numAttributes)
- {
- return numAttributes < other.numAttributes;
- }
-
- if (flags != other.flags)
- {
- return flags < other.flags;
- }
-
- return memcmp(attributeData, other.attributeData, sizeof(uint32_t) * numAttributes) < 0;
+ return (numAttributes == other.numAttributes) && (flags == other.flags) &&
+ (attributeData == other.attributeData);
}
-InputLayoutCache::InputLayoutCache() : mUnsortedAttributesCount(0), mCacheSize(kDefaultCacheSize)
+InputLayoutCache::InputLayoutCache()
+ : mLayoutCache(kDefaultCacheSize * 2), mPointSpriteVertexBuffer(), mPointSpriteIndexBuffer()
{
- mCounter = 0;
- mDevice = NULL;
- mDeviceContext = NULL;
- mCurrentIL = NULL;
-
- for (unsigned int i = 0; i < gl::MAX_VERTEX_ATTRIBS; i++)
- {
- mCurrentBuffers[i] = NULL;
- mCurrentVertexStrides[i] = static_cast<UINT>(-1);
- mCurrentVertexOffsets[i] = static_cast<UINT>(-1);
- }
- mPointSpriteVertexBuffer = NULL;
- mPointSpriteIndexBuffer = NULL;
}
InputLayoutCache::~InputLayoutCache()
{
- clear();
-}
-
-void InputLayoutCache::initialize(ID3D11Device *device, ID3D11DeviceContext *context)
-{
- clear();
- mDevice = device;
- mDeviceContext = context;
- mFeatureLevel = device->GetFeatureLevel();
}
void InputLayoutCache::clear()
{
- for (auto &layout : mLayoutMap)
- {
- SafeRelease(layout.second);
- }
- mLayoutMap.clear();
- SafeRelease(mPointSpriteVertexBuffer);
- SafeRelease(mPointSpriteIndexBuffer);
- markDirty();
-}
-
-void InputLayoutCache::markDirty()
-{
- mCurrentIL = NULL;
- for (unsigned int i = 0; i < gl::MAX_VERTEX_ATTRIBS; i++)
- {
- mCurrentBuffers[i] = NULL;
- mCurrentVertexStrides[i] = static_cast<UINT>(-1);
- mCurrentVertexOffsets[i] = static_cast<UINT>(-1);
- }
- mUnsortedAttributesCount = 0;
+ mLayoutCache.Clear();
+ mPointSpriteVertexBuffer.reset();
+ mPointSpriteIndexBuffer.reset();
}
gl::Error InputLayoutCache::applyVertexBuffers(
- const std::vector<TranslatedAttribute> &unsortedAttributes,
+ const gl::Context *context,
+ const std::vector<const TranslatedAttribute *> &currentAttributes,
GLenum mode,
- gl::Program *program,
- TranslatedIndexData *indexInfo,
- GLsizei numIndicesPerInstance)
+ GLint start,
+ bool isIndexedRendering)
{
- ASSERT(mDevice && mDeviceContext);
-
+ Renderer11 *renderer = GetImplAs<Context11>(context)->getRenderer();
+ const gl::State &state = context->getGLState();
+ auto *stateManager = renderer->getStateManager();
+ gl::Program *program = state.getProgram();
ProgramD3D *programD3D = GetImplAs<ProgramD3D>(program);
bool programUsesInstancedPointSprites = programD3D->usesPointSize() && programD3D->usesInstancedPointSpriteEmulation();
bool instancedPointSpritesActive = programUsesInstancedPointSprites && (mode == GL_POINTS);
- SortedIndexArray sortedSemanticIndices;
- mSortedAttributes.fill(nullptr);
- mUnsortedAttributesCount = unsortedAttributes.size();
-
- programD3D->sortAttributesByLayout(unsortedAttributes, sortedSemanticIndices.data(),
- mSortedAttributes.data());
-
- // If we are using FL 9_3, make sure the first attribute is not instanced
- if (mFeatureLevel <= D3D_FEATURE_LEVEL_9_3 && !unsortedAttributes.empty())
- {
- if (mSortedAttributes[0]->divisor > 0)
- {
- Optional<size_t> firstNonInstancedIndex =
- FindFirstNonInstanced(mSortedAttributes, unsortedAttributes.size());
- if (firstNonInstancedIndex.valid())
- {
- size_t index = firstNonInstancedIndex.value();
- std::swap(mSortedAttributes[0], mSortedAttributes[index]);
- std::swap(sortedSemanticIndices[0], sortedSemanticIndices[index]);
- }
- }
- }
-
- gl::Error error = updateInputLayout(program, mode, mSortedAttributes, sortedSemanticIndices,
- unsortedAttributes.size(), numIndicesPerInstance);
- if (error.isError())
- {
- return error;
- }
-
- bool dirtyBuffers = false;
- size_t minDiff = gl::MAX_VERTEX_ATTRIBS;
- size_t maxDiff = 0;
-
// Note that if we use instance emulation, we reserve the first buffer slot.
size_t reservedBuffers = GetReservedBufferCount(programUsesInstancedPointSprites);
for (size_t attribIndex = 0; attribIndex < (gl::MAX_VERTEX_ATTRIBS - reservedBuffers);
++attribIndex)
{
- ID3D11Buffer *buffer = NULL;
- UINT vertexStride = 0;
- UINT vertexOffset = 0;
+ ID3D11Buffer *buffer = nullptr;
+ UINT vertexStride = 0;
+ UINT vertexOffset = 0;
- const auto &attrib = *mSortedAttributes[attribIndex];
-
- if (attribIndex < unsortedAttributes.size() && attrib.active)
+ if (attribIndex < currentAttributes.size())
{
- VertexBuffer11 *vertexBuffer = GetAs<VertexBuffer11>(attrib.vertexBuffer);
- Buffer11 *bufferStorage = attrib.storage ? GetAs<Buffer11>(attrib.storage) : nullptr;
+ const auto &attrib = *currentAttributes[attribIndex];
+ Buffer11 *bufferStorage = attrib.storage ? GetAs<Buffer11>(attrib.storage) : nullptr;
// If indexed pointsprite emulation is active, then we need to take a less efficent code path.
// Emulated indexed pointsprite rendering requires that the vertex buffers match exactly to
@@ -261,18 +159,18 @@ gl::Error InputLayoutCache::applyVertexBuffers(
// on the number of points indicated by the index list or how many duplicates are found on the index list.
if (bufferStorage == nullptr)
{
- buffer = vertexBuffer->getBuffer();
+ ASSERT(attrib.vertexBuffer.get());
+ buffer = GetAs<VertexBuffer11>(attrib.vertexBuffer.get())->getBuffer().get();
}
- else if (instancedPointSpritesActive && (indexInfo != nullptr))
+ else if (instancedPointSpritesActive && isIndexedRendering)
{
+ VertexArray11 *vao11 = GetImplAs<VertexArray11>(state.getVertexArray());
+ ASSERT(vao11->isCachedIndexInfoValid());
+ TranslatedIndexData *indexInfo = vao11->getCachedIndexInfo();
if (indexInfo->srcIndexData.srcBuffer != nullptr)
{
const uint8_t *bufferData = nullptr;
- error = indexInfo->srcIndexData.srcBuffer->getData(&bufferData);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(indexInfo->srcIndexData.srcBuffer->getData(context, &bufferData));
ASSERT(bufferData != nullptr);
ptrdiff_t offset =
@@ -281,31 +179,24 @@ gl::Error InputLayoutCache::applyVertexBuffers(
indexInfo->srcIndexData.srcIndices = bufferData + offset;
}
- buffer = bufferStorage->getEmulatedIndexedBuffer(&indexInfo->srcIndexData, &attrib);
+ ANGLE_TRY_RESULT(bufferStorage->getEmulatedIndexedBuffer(
+ context, &indexInfo->srcIndexData, attrib, start),
+ buffer);
}
else
{
- buffer = bufferStorage->getBuffer(BUFFER_USAGE_VERTEX_OR_TRANSFORM_FEEDBACK);
+ ANGLE_TRY_RESULT(
+ bufferStorage->getBuffer(context, BUFFER_USAGE_VERTEX_OR_TRANSFORM_FEEDBACK),
+ buffer);
}
vertexStride = attrib.stride;
- vertexOffset = attrib.offset;
+ ANGLE_TRY_RESULT(attrib.computeOffset(start), vertexOffset);
}
size_t bufferIndex = reservedBuffers + attribIndex;
- if (buffer != mCurrentBuffers[bufferIndex] ||
- vertexStride != mCurrentVertexStrides[bufferIndex] ||
- vertexOffset != mCurrentVertexOffsets[bufferIndex])
- {
- dirtyBuffers = true;
- minDiff = std::min(minDiff, bufferIndex);
- maxDiff = std::max(maxDiff, bufferIndex);
-
- mCurrentBuffers[bufferIndex] = buffer;
- mCurrentVertexStrides[bufferIndex] = vertexStride;
- mCurrentVertexOffsets[bufferIndex] = vertexOffset;
- }
+ stateManager->queueVertexBufferChange(bufferIndex, buffer, vertexStride, vertexOffset);
}
// Instanced PointSprite emulation requires two additional ID3D11Buffers. A vertex buffer needs
@@ -317,10 +208,9 @@ gl::Error InputLayoutCache::applyVertexBuffers(
// handle missing vertex data and will TDR the system.
if (programUsesInstancedPointSprites)
{
- HRESULT result = S_OK;
const UINT pointSpriteVertexStride = sizeof(float) * 5;
- if (!mPointSpriteVertexBuffer)
+ if (!mPointSpriteVertexBuffer.valid())
{
static const float pointSpriteVertices[] =
{
@@ -342,25 +232,16 @@ gl::Error InputLayoutCache::applyVertexBuffers(
vertexBufferDesc.MiscFlags = 0;
vertexBufferDesc.StructureByteStride = 0;
- result = mDevice->CreateBuffer(&vertexBufferDesc, &vertexBufferData, &mPointSpriteVertexBuffer);
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create instanced pointsprite emulation vertex buffer, HRESULT: 0x%08x", result);
- }
+ ANGLE_TRY(renderer->allocateResource(vertexBufferDesc, &vertexBufferData,
+ &mPointSpriteVertexBuffer));
}
- mCurrentBuffers[0] = mPointSpriteVertexBuffer;
// Set the stride to 0 if GL_POINTS mode is not being used to instruct the driver to avoid
// indexing into the vertex buffer.
- mCurrentVertexStrides[0] = instancedPointSpritesActive ? pointSpriteVertexStride : 0;
- mCurrentVertexOffsets[0] = 0;
-
- // Update maxDiff to include the additional point sprite vertex buffer
- // to ensure that IASetVertexBuffers uses the correct buffer count.
- minDiff = 0;
- maxDiff = std::max(maxDiff, static_cast<size_t>(0));
+ UINT stride = instancedPointSpritesActive ? pointSpriteVertexStride : 0;
+ stateManager->queueVertexBufferChange(0, mPointSpriteVertexBuffer.get(), stride, 0);
- if (!mPointSpriteIndexBuffer)
+ if (!mPointSpriteIndexBuffer.valid())
{
// Create an index buffer and set it for pointsprite rendering
static const unsigned short pointSpriteIndices[] =
@@ -377,12 +258,8 @@ gl::Error InputLayoutCache::applyVertexBuffers(
indexBufferDesc.MiscFlags = 0;
indexBufferDesc.StructureByteStride = 0;
- result = mDevice->CreateBuffer(&indexBufferDesc, &indexBufferData, &mPointSpriteIndexBuffer);
- if (FAILED(result))
- {
- SafeRelease(mPointSpriteVertexBuffer);
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create instanced pointsprite emulation index buffer, HRESULT: 0x%08x", result);
- }
+ ANGLE_TRY(renderer->allocateResource(indexBufferDesc, &indexBufferData,
+ &mPointSpriteIndexBuffer));
}
if (instancedPointSpritesActive)
@@ -391,51 +268,51 @@ gl::Error InputLayoutCache::applyVertexBuffers(
// non-indexed rendering path in ANGLE (DrawArrays). This means that applyIndexBuffer()
// on the renderer will not be called and setting this buffer here ensures that the
// rendering path will contain the correct index buffers.
- mDeviceContext->IASetIndexBuffer(mPointSpriteIndexBuffer, DXGI_FORMAT_R16_UINT, 0);
+ stateManager->setIndexBuffer(mPointSpriteIndexBuffer.get(), DXGI_FORMAT_R16_UINT, 0);
}
}
- if (dirtyBuffers)
- {
- ASSERT(minDiff <= maxDiff && maxDiff < gl::MAX_VERTEX_ATTRIBS);
- mDeviceContext->IASetVertexBuffers(
- static_cast<UINT>(minDiff), static_cast<UINT>(maxDiff - minDiff + 1),
- mCurrentBuffers + minDiff, mCurrentVertexStrides + minDiff,
- mCurrentVertexOffsets + minDiff);
- }
-
- return gl::Error(GL_NO_ERROR);
+ stateManager->applyVertexBufferChanges();
+ return gl::NoError();
}
-gl::Error InputLayoutCache::updateVertexOffsetsForPointSpritesEmulation(GLsizei emulatedInstanceId)
+gl::Error InputLayoutCache::updateVertexOffsetsForPointSpritesEmulation(
+ Renderer11 *renderer,
+ const std::vector<const TranslatedAttribute *> &currentAttributes,
+ GLint startVertex,
+ GLsizei emulatedInstanceId)
{
+ auto *stateManager = renderer->getStateManager();
+
size_t reservedBuffers = GetReservedBufferCount(true);
- for (size_t attribIndex = 0; attribIndex < mUnsortedAttributesCount; ++attribIndex)
+ for (size_t attribIndex = 0; attribIndex < currentAttributes.size(); ++attribIndex)
{
- const auto &attrib = *mSortedAttributes[attribIndex];
+ const auto &attrib = *currentAttributes[attribIndex];
size_t bufferIndex = reservedBuffers + attribIndex;
- if (attrib.active && attrib.divisor > 0)
+ if (attrib.divisor > 0)
{
- mCurrentVertexOffsets[bufferIndex] =
- attrib.offset + (attrib.stride * (emulatedInstanceId / attrib.divisor));
+ unsigned int offset = 0;
+ ANGLE_TRY_RESULT(attrib.computeOffset(startVertex), offset);
+ offset += (attrib.stride * (emulatedInstanceId / attrib.divisor));
+ stateManager->queueVertexOffsetChange(bufferIndex, offset);
}
}
- mDeviceContext->IASetVertexBuffers(0, gl::MAX_VERTEX_ATTRIBS, mCurrentBuffers,
- mCurrentVertexStrides, mCurrentVertexOffsets);
-
- return gl::Error(GL_NO_ERROR);
+ stateManager->applyVertexBufferChanges();
+ return gl::NoError();
}
-gl::Error InputLayoutCache::updateInputLayout(gl::Program *program,
- GLenum mode,
- const SortedAttribArray &sortedAttributes,
- const SortedIndexArray &sortedSemanticIndices,
- size_t attribCount,
- GLsizei numIndicesPerInstance)
+gl::Error InputLayoutCache::updateInputLayout(
+ Renderer11 *renderer,
+ const gl::State &state,
+ const std::vector<const TranslatedAttribute *> &currentAttributes,
+ GLenum mode,
+ const AttribIndexArray &sortedSemanticIndices,
+ const DrawCallVertexParams &vertexParams)
{
- const std::vector<sh::Attribute> &shaderAttributes = program->getAttributes();
+ gl::Program *program = state.getProgram();
+ const auto &shaderAttributes = program->getAttributes();
PackedAttributeLayout layout;
ProgramD3D *programD3D = GetImplAs<ProgramD3D>(program);
@@ -453,90 +330,70 @@ gl::Error InputLayoutCache::updateInputLayout(gl::Program *program,
layout.flags |= PackedAttributeLayout::FLAG_INSTANCED_SPRITES_ACTIVE;
}
- if (numIndicesPerInstance > 0)
+ if (vertexParams.instances() > 0)
{
layout.flags |= PackedAttributeLayout::FLAG_INSTANCED_RENDERING_ACTIVE;
}
- const auto &semanticToLocation = programD3D->getAttributesByLayout();
+ const auto &attribs = state.getVertexArray()->getVertexAttributes();
+ const auto &bindings = state.getVertexArray()->getVertexBindings();
+ const auto &locationToSemantic = programD3D->getAttribLocationToD3DSemantics();
+ int divisorMultiplier = program->usesMultiview() ? program->getNumViews() : 1;
- for (size_t attribIndex = 0; attribIndex < attribCount; ++attribIndex)
+ for (size_t attribIndex : program->getActiveAttribLocationsMask())
{
- const auto &attrib = *sortedAttributes[attribIndex];
- int sortedIndex = sortedSemanticIndices[attribIndex];
-
- if (!attrib.active)
- continue;
-
- gl::VertexFormatType vertexFormatType =
- gl::GetVertexFormatType(*attrib.attribute, attrib.currentValueType);
-
// Record the type of the associated vertex shader vector in our key
// This will prevent mismatched vertex shaders from using the same input layout
- GLenum glslElementType =
- GetGLSLAttributeType(shaderAttributes, semanticToLocation[sortedIndex]);
+ GLenum glslElementType = GetGLSLAttributeType(shaderAttributes, attribIndex);
- layout.addAttributeData(glslElementType, sortedIndex, vertexFormatType, attrib.divisor);
+ const auto &attrib = attribs[attribIndex];
+ const auto &binding = bindings[attrib.bindingIndex];
+ int d3dSemantic = locationToSemantic[attribIndex];
+
+ const auto &currentValue =
+ state.getVertexAttribCurrentValue(static_cast<unsigned int>(attribIndex));
+ gl::VertexFormatType vertexFormatType = gl::GetVertexFormatType(attrib, currentValue.Type);
+
+ layout.addAttributeData(glslElementType, d3dSemantic, vertexFormatType,
+ binding.getDivisor() * divisorMultiplier);
}
- ID3D11InputLayout *inputLayout = nullptr;
+ const d3d11::InputLayout *inputLayout = nullptr;
if (layout.numAttributes > 0 || layout.flags != 0)
{
- auto layoutMapIt = mLayoutMap.find(layout);
- if (layoutMapIt != mLayoutMap.end())
+ auto it = mLayoutCache.Get(layout);
+ if (it != mLayoutCache.end())
{
- inputLayout = layoutMapIt->second;
+ inputLayout = &it->second;
}
else
{
- gl::Error error =
- createInputLayout(sortedAttributes, sortedSemanticIndices, attribCount, mode,
- program, numIndicesPerInstance, &inputLayout);
- if (error.isError())
- {
- return error;
- }
- if (mLayoutMap.size() >= mCacheSize)
- {
- TRACE("Overflowed the limit of %u input layouts, purging half the cache.",
- mCacheSize);
+ angle::TrimCache(mLayoutCache.max_size() / 2, kGCLimit, "input layout", &mLayoutCache);
- // Randomly release every second element
- auto it = mLayoutMap.begin();
- while (it != mLayoutMap.end())
- {
- it++;
- if (it != mLayoutMap.end())
- {
- // c++11 erase allows us to easily delete the current iterator.
- SafeRelease(it->second);
- it = mLayoutMap.erase(it);
- }
- }
- }
+ d3d11::InputLayout newInputLayout;
+ ANGLE_TRY(createInputLayout(renderer, sortedSemanticIndices, currentAttributes, mode,
+ program, vertexParams, &newInputLayout));
- mLayoutMap[layout] = inputLayout;
+ auto insertIt = mLayoutCache.Put(layout, std::move(newInputLayout));
+ inputLayout = &insertIt->second;
}
}
- if (inputLayout != mCurrentIL)
- {
- mDeviceContext->IASetInputLayout(inputLayout);
- mCurrentIL = inputLayout;
- }
-
- return gl::Error(GL_NO_ERROR);
+ renderer->getStateManager()->setInputLayout(inputLayout);
+ return gl::NoError();
}
-gl::Error InputLayoutCache::createInputLayout(const SortedAttribArray &sortedAttributes,
- const SortedIndexArray &sortedSemanticIndices,
- size_t attribCount,
- GLenum mode,
- gl::Program *program,
- GLsizei numIndicesPerInstance,
- ID3D11InputLayout **inputLayoutOut)
+gl::Error InputLayoutCache::createInputLayout(
+ Renderer11 *renderer,
+ const AttribIndexArray &sortedSemanticIndices,
+ const std::vector<const TranslatedAttribute *> &currentAttributes,
+ GLenum mode,
+ gl::Program *program,
+ const DrawCallVertexParams &vertexParams,
+ d3d11::InputLayout *inputLayoutOut)
{
ProgramD3D *programD3D = GetImplAs<ProgramD3D>(program);
+ auto featureLevel = renderer->getRenderer11DeviceCaps().featureLevel;
bool programUsesInstancedPointSprites =
programD3D->usesPointSize() && programD3D->usesInstancedPointSpriteEmulation();
@@ -544,20 +401,17 @@ gl::Error InputLayoutCache::createInputLayout(const SortedAttribArray &sortedAtt
unsigned int inputElementCount = 0;
std::array<D3D11_INPUT_ELEMENT_DESC, gl::MAX_VERTEX_ATTRIBS> inputElements;
- for (size_t attribIndex = 0; attribIndex < attribCount; ++attribIndex)
+ for (size_t attribIndex = 0; attribIndex < currentAttributes.size(); ++attribIndex)
{
- const auto &attrib = *sortedAttributes[attribIndex];
+ const auto &attrib = *currentAttributes[attribIndex];
const int sortedIndex = sortedSemanticIndices[attribIndex];
- if (!attrib.active)
- continue;
-
D3D11_INPUT_CLASSIFICATION inputClass =
attrib.divisor > 0 ? D3D11_INPUT_PER_INSTANCE_DATA : D3D11_INPUT_PER_VERTEX_DATA;
const auto &vertexFormatType =
gl::GetVertexFormatType(*attrib.attribute, attrib.currentValueType);
- const auto &vertexFormatInfo = d3d11::GetVertexFormatInfo(vertexFormatType, mFeatureLevel);
+ const auto &vertexFormatInfo = d3d11::GetVertexFormatInfo(vertexFormatType, featureLevel);
auto *inputElement = &inputElements[inputElementCount];
@@ -584,23 +438,28 @@ gl::Error InputLayoutCache::createInputLayout(const SortedAttribArray &sortedAtt
// doesn't support OpenGL ES 3.0.
// As per the spec for ANGLE_instanced_arrays, not all attributes can be instanced
// simultaneously, so a non-instanced element must exist.
+
+ GLsizei numIndicesPerInstance = 0;
+ if (vertexParams.instances() > 0)
+ {
+ // This may trigger an evaluation of the index range.
+ numIndicesPerInstance = vertexParams.vertexCount();
+ }
+
for (size_t elementIndex = 0; elementIndex < inputElementCount; ++elementIndex)
{
- if (sortedAttributes[elementIndex]->active)
+ // If rendering points and instanced pointsprite emulation is being used, the
+ // inputClass is required to be configured as per instance data
+ if (mode == GL_POINTS)
{
- // If rendering points and instanced pointsprite emulation is being used, the
- // inputClass is required to be configured as per instance data
- if (mode == GL_POINTS)
+ inputElements[elementIndex].InputSlotClass = D3D11_INPUT_PER_INSTANCE_DATA;
+ inputElements[elementIndex].InstanceDataStepRate = 1;
+ if (numIndicesPerInstance > 0 && currentAttributes[elementIndex]->divisor > 0)
{
- inputElements[elementIndex].InputSlotClass = D3D11_INPUT_PER_INSTANCE_DATA;
- inputElements[elementIndex].InstanceDataStepRate = 1;
- if (numIndicesPerInstance > 0 && sortedAttributes[elementIndex]->divisor > 0)
- {
- inputElements[elementIndex].InstanceDataStepRate = numIndicesPerInstance;
- }
+ inputElements[elementIndex].InstanceDataStepRate = numIndicesPerInstance;
}
- inputElements[elementIndex].InputSlot++;
}
+ inputElements[elementIndex].InputSlot++;
}
inputElements[inputElementCount].SemanticName = "SPRITEPOSITION";
@@ -622,28 +481,23 @@ gl::Error InputLayoutCache::createInputLayout(const SortedAttribArray &sortedAtt
inputElementCount++;
}
- const gl::InputLayout &shaderInputLayout = GetInputLayout(sortedAttributes, attribCount);
-
ShaderExecutableD3D *shader = nullptr;
- gl::Error error =
- programD3D->getVertexExecutableForInputLayout(shaderInputLayout, &shader, nullptr);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(programD3D->getVertexExecutableForCachedInputLayout(&shader, nullptr));
ShaderExecutableD3D *shader11 = GetAs<ShaderExecutable11>(shader);
- HRESULT result =
- mDevice->CreateInputLayout(inputElements.data(), inputElementCount, shader11->getFunction(),
- shader11->getLength(), inputLayoutOut);
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY,
- "Failed to create internal input layout, HRESULT: 0x%08x", result);
- }
+ InputElementArray inputElementArray(inputElements.data(), inputElementCount);
+ ShaderData vertexShaderData(shader11->getFunction(), shader11->getLength());
- return gl::Error(GL_NO_ERROR);
+ ANGLE_TRY(renderer->allocateResource(inputElementArray, &vertexShaderData, inputLayoutOut));
+ return gl::NoError();
+}
+
+void InputLayoutCache::setCacheSize(size_t newCacheSize)
+{
+ // Forces a reset of the cache.
+ LayoutCache newCache(newCacheSize);
+ mLayoutCache.Swap(newCache);
}
} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/InputLayoutCache.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/InputLayoutCache.h
index e208ae3c64..8d7c7dd0f0 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/InputLayoutCache.h
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/InputLayoutCache.h
@@ -20,12 +20,55 @@
#include "common/angleutils.h"
#include "libANGLE/Constants.h"
#include "libANGLE/Error.h"
+#include "libANGLE/SizedMRUCache.h"
#include "libANGLE/formatutils.h"
+#include "libANGLE/renderer/d3d/RendererD3D.h"
+#include "libANGLE/renderer/d3d/d3d11/ResourceManager11.h"
+
+namespace rx
+{
+class DrawCallVertexParams;
+struct PackedAttributeLayout
+{
+ PackedAttributeLayout();
+ PackedAttributeLayout(const PackedAttributeLayout &other);
+
+ void addAttributeData(GLenum glType,
+ UINT semanticIndex,
+ gl::VertexFormatType vertexFormatType,
+ unsigned int divisor);
+
+ bool operator==(const PackedAttributeLayout &other) const;
+
+ enum Flags
+ {
+ FLAG_USES_INSTANCED_SPRITES = 0x1,
+ FLAG_INSTANCED_SPRITES_ACTIVE = 0x2,
+ FLAG_INSTANCED_RENDERING_ACTIVE = 0x4,
+ };
+
+ uint32_t numAttributes;
+ uint32_t flags;
+ std::array<uint32_t, gl::MAX_VERTEX_ATTRIBS> attributeData;
+};
+} // namespace rx
+
+namespace std
+{
+template <>
+struct hash<rx::PackedAttributeLayout>
+{
+ size_t operator()(const rx::PackedAttributeLayout &value) const
+ {
+ return angle::ComputeGenericHash(value);
+ }
+};
+} // namespace std
namespace gl
{
class Program;
-}
+} // namespace gl
namespace rx
{
@@ -33,91 +76,58 @@ struct TranslatedAttribute;
struct TranslatedIndexData;
struct SourceIndexData;
class ProgramD3D;
-
-using SortedAttribArray = std::array<const TranslatedAttribute *, gl::MAX_VERTEX_ATTRIBS>;
-using SortedIndexArray = std::array<int, gl::MAX_VERTEX_ATTRIBS>;
+class Renderer11;
class InputLayoutCache : angle::NonCopyable
{
public:
InputLayoutCache();
- virtual ~InputLayoutCache();
+ ~InputLayoutCache();
- void initialize(ID3D11Device *device, ID3D11DeviceContext *context);
void clear();
- void markDirty();
- gl::Error applyVertexBuffers(const std::vector<TranslatedAttribute> &attributes,
+ gl::Error applyVertexBuffers(const gl::Context *context,
+ const std::vector<const TranslatedAttribute *> &currentAttributes,
GLenum mode,
- gl::Program *program,
- TranslatedIndexData *indexInfo,
- GLsizei numIndicesPerInstance);
+ GLint start,
+ bool isIndexedRendering);
- gl::Error updateVertexOffsetsForPointSpritesEmulation(GLsizei emulatedInstanceId);
+ gl::Error updateVertexOffsetsForPointSpritesEmulation(
+ Renderer11 *renderer,
+ const std::vector<const TranslatedAttribute *> &currentAttributes,
+ GLint startVertex,
+ GLsizei emulatedInstanceId);
// Useful for testing
- void setCacheSize(unsigned int cacheSize) { mCacheSize = cacheSize; }
-
- private:
- struct PackedAttributeLayout
- {
- PackedAttributeLayout()
- : numAttributes(0),
- flags(0)
- {
- }
-
- void addAttributeData(GLenum glType,
- UINT semanticIndex,
- gl::VertexFormatType vertexFormatType,
- unsigned int divisor);
-
- bool operator<(const PackedAttributeLayout &other) const;
-
- enum Flags
- {
- FLAG_USES_INSTANCED_SPRITES = 0x1,
- FLAG_INSTANCED_SPRITES_ACTIVE = 0x2,
- FLAG_INSTANCED_RENDERING_ACTIVE = 0x4,
- };
-
- size_t numAttributes;
- unsigned int flags;
- uint32_t attributeData[gl::MAX_VERTEX_ATTRIBS];
- };
+ void setCacheSize(size_t newCacheSize);
- gl::Error updateInputLayout(gl::Program *program,
+ gl::Error updateInputLayout(Renderer11 *renderer,
+ const gl::State &state,
+ const std::vector<const TranslatedAttribute *> &currentAttributes,
GLenum mode,
- const SortedAttribArray &sortedAttributes,
- const SortedIndexArray &sortedSemanticIndices,
- size_t attribCount,
- GLsizei numIndicesPerInstance);
- gl::Error createInputLayout(const SortedAttribArray &sortedAttributes,
- const SortedIndexArray &sortedSemanticIndices,
- size_t attribCount,
+ const AttribIndexArray &sortedSemanticIndices,
+ const DrawCallVertexParams &vertexParams);
+
+ private:
+ gl::Error createInputLayout(Renderer11 *renderer,
+ const AttribIndexArray &sortedSemanticIndices,
+ const std::vector<const TranslatedAttribute *> &currentAttributes,
GLenum mode,
gl::Program *program,
- GLsizei numIndicesPerInstance,
- ID3D11InputLayout **inputLayoutOut);
-
- std::map<PackedAttributeLayout, ID3D11InputLayout *> mLayoutMap;
+ const DrawCallVertexParams &vertexParams,
+ d3d11::InputLayout *inputLayoutOut);
- ID3D11InputLayout *mCurrentIL;
- ID3D11Buffer *mCurrentBuffers[gl::MAX_VERTEX_ATTRIBS];
- UINT mCurrentVertexStrides[gl::MAX_VERTEX_ATTRIBS];
- UINT mCurrentVertexOffsets[gl::MAX_VERTEX_ATTRIBS];
- SortedAttribArray mSortedAttributes;
- size_t mUnsortedAttributesCount;
+ // Starting cache size.
+ static constexpr size_t kDefaultCacheSize = 1024;
- ID3D11Buffer *mPointSpriteVertexBuffer;
- ID3D11Buffer *mPointSpriteIndexBuffer;
+ // The cache tries to clean up this many states at once.
+ static constexpr size_t kGCLimit = 128;
- unsigned int mCacheSize;
- unsigned long long mCounter;
+ using LayoutCache = angle::base::HashingMRUCache<PackedAttributeLayout, d3d11::InputLayout>;
+ LayoutCache mLayoutCache;
- ID3D11Device *mDevice;
- ID3D11DeviceContext *mDeviceContext;
- D3D_FEATURE_LEVEL mFeatureLevel;
+ d3d11::Buffer mPointSpriteVertexBuffer;
+ d3d11::Buffer mPointSpriteIndexBuffer;
};
} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/NativeWindow.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/NativeWindow.h
deleted file mode 100644
index 612b06bb10..0000000000
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/NativeWindow.h
+++ /dev/null
@@ -1,97 +0,0 @@
-//
-// Copyright (c) 2014 The ANGLE Project Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-//
-
-// NativeWindow.h: Defines NativeWindow, a class for managing and
-// performing operations on an EGLNativeWindowType.
-// It is used for HWND (Desktop Windows) and IInspectable objects
-//(Windows Store Applications).
-
-#ifndef LIBANGLE_RENDERER_D3D_D3D11_NATIVEWINDOW_H_
-#define LIBANGLE_RENDERER_D3D_D3D11_NATIVEWINDOW_H_
-
-#include "common/debug.h"
-#include "common/platform.h"
-
-#include <EGL/eglplatform.h>
-#include "libANGLE/Config.h"
-
-// DXGISwapChain and DXGIFactory are typedef'd to specific required
-// types. The HWND NativeWindow implementation requires IDXGISwapChain
-// and IDXGIFactory and the Windows Store NativeWindow
-// implementation requires IDXGISwapChain1 and IDXGIFactory2.
-#if defined(ANGLE_ENABLE_WINDOWS_STORE)
-typedef IDXGISwapChain1 DXGISwapChain;
-typedef IDXGIFactory2 DXGIFactory;
-
-#include <wrl.h>
-#include <wrl/wrappers/corewrappers.h>
-#include <windows.applicationmodel.core.h>
-#include <memory>
-
-namespace rx
-{
-class InspectableNativeWindow;
-}
-
-using namespace Microsoft::WRL;
-using namespace Microsoft::WRL::Wrappers;
-
-#elif defined(ANGLE_ENABLE_D3D11)
-typedef IDXGISwapChain DXGISwapChain;
-typedef IDXGIFactory DXGIFactory;
-#endif
-
-typedef interface IDCompositionDevice IDCompositionDevice;
-typedef interface IDCompositionTarget IDCompositionTarget;
-typedef interface IDCompositionVisual IDCompositionVisual;
-
-namespace rx
-{
-
-class NativeWindow
-{
- public:
- enum RotationFlags { RotateNone = 0, RotateLeft = 1, RotateRight = 2 };
- explicit NativeWindow(EGLNativeWindowType window,
- const egl::Config *config,
- bool directComposition);
-
- ~NativeWindow();
- bool initialize();
- bool getClientRect(LPRECT rect);
- bool isIconic();
-#if defined(ANGLE_ENABLE_WINDOWS_STORE) && (WINAPI_FAMILY == WINAPI_FAMILY_PHONE_APP)
- RotationFlags rotationFlags() const;
-#endif
- static bool isValidNativeWindow(EGLNativeWindowType window);
-
-#if defined(ANGLE_ENABLE_D3D11)
- HRESULT createSwapChain(ID3D11Device* device, DXGIFactory* factory,
- DXGI_FORMAT format, UINT width, UINT height,
- DXGISwapChain** swapChain);
-#endif
-
- inline EGLNativeWindowType getNativeWindow() const { return mWindow; }
-
- void commitChange();
-
- private:
- EGLNativeWindowType mWindow;
-
- bool mDirectComposition;
- IDCompositionDevice *mDevice;
- IDCompositionTarget *mCompositionTarget;
- IDCompositionVisual *mVisual;
- const egl::Config *mConfig;
-#if defined(ANGLE_ENABLE_WINDOWS_STORE)
- std::shared_ptr<InspectableNativeWindow> mImpl;
-#endif
-
-};
-
-}
-
-#endif // LIBANGLE_RENDERER_D3D_D3D11_NATIVEWINDOW_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/NativeWindow11.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/NativeWindow11.h
new file mode 100644
index 0000000000..ab234d4450
--- /dev/null
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/NativeWindow11.h
@@ -0,0 +1,38 @@
+//
+// Copyright (c) 2016 The ANGLE Project Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+//
+
+// NativeWindow11.h: Defines NativeWindow11, a class for managing and performing operations on an
+// EGLNativeWindowType for the D3D11 renderer.
+
+#ifndef LIBANGLE_RENDERER_D3D_D3D11_NATIVEWINDOW11_H_
+#define LIBANGLE_RENDERER_D3D_D3D11_NATIVEWINDOW11_H_
+
+#include "common/debug.h"
+#include "common/platform.h"
+
+#include "libANGLE/Config.h"
+#include "libANGLE/renderer/d3d/NativeWindowD3D.h"
+
+namespace rx
+{
+
+class NativeWindow11 : public NativeWindowD3D
+{
+ public:
+ NativeWindow11(EGLNativeWindowType window) : NativeWindowD3D(window) {}
+
+ virtual HRESULT createSwapChain(ID3D11Device *device,
+ IDXGIFactory *factory,
+ DXGI_FORMAT format,
+ UINT width,
+ UINT height,
+ UINT samples,
+ IDXGISwapChain **swapChain) = 0;
+ virtual void commitChange() = 0;
+};
+} // namespace rx
+
+#endif // LIBANGLE_RENDERER_D3D_D3D11_NATIVEWINDOW11_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/PixelTransfer11.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/PixelTransfer11.cpp
index dfc521f14f..7d7ecb0976 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/PixelTransfer11.cpp
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/PixelTransfer11.cpp
@@ -36,40 +36,25 @@ namespace rx
PixelTransfer11::PixelTransfer11(Renderer11 *renderer)
: mRenderer(renderer),
mResourcesLoaded(false),
- mBufferToTextureVS(NULL),
- mBufferToTextureGS(NULL),
- mParamsConstantBuffer(NULL),
- mCopyRasterizerState(NULL),
- mCopyDepthStencilState(NULL)
+ mBufferToTextureVS(),
+ mBufferToTextureGS(),
+ mParamsConstantBuffer(),
+ mCopyRasterizerState(),
+ mCopyDepthStencilState()
{
}
PixelTransfer11::~PixelTransfer11()
{
- for (auto shaderMapIt = mBufferToTexturePSMap.begin(); shaderMapIt != mBufferToTexturePSMap.end(); shaderMapIt++)
- {
- SafeRelease(shaderMapIt->second);
- }
-
- mBufferToTexturePSMap.clear();
-
- SafeRelease(mBufferToTextureVS);
- SafeRelease(mBufferToTextureGS);
- SafeRelease(mParamsConstantBuffer);
- SafeRelease(mCopyRasterizerState);
- SafeRelease(mCopyDepthStencilState);
}
gl::Error PixelTransfer11::loadResources()
{
if (mResourcesLoaded)
{
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
- HRESULT result = S_OK;
- ID3D11Device *device = mRenderer->getDevice();
-
D3D11_RASTERIZER_DESC rasterDesc;
rasterDesc.FillMode = D3D11_FILL_SOLID;
rasterDesc.CullMode = D3D11_CULL_NONE;
@@ -82,12 +67,7 @@ gl::Error PixelTransfer11::loadResources()
rasterDesc.MultisampleEnable = FALSE;
rasterDesc.AntialiasedLineEnable = FALSE;
- result = device->CreateRasterizerState(&rasterDesc, &mCopyRasterizerState);
- ASSERT(SUCCEEDED(result));
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal pixel transfer rasterizer state, result: 0x%X.", result);
- }
+ ANGLE_TRY(mRenderer->allocateResource(rasterDesc, &mCopyRasterizerState));
D3D11_DEPTH_STENCIL_DESC depthStencilDesc;
depthStencilDesc.DepthEnable = true;
@@ -105,12 +85,7 @@ gl::Error PixelTransfer11::loadResources()
depthStencilDesc.BackFace.StencilPassOp = D3D11_STENCIL_OP_KEEP;
depthStencilDesc.BackFace.StencilFunc = D3D11_COMPARISON_ALWAYS;
- result = device->CreateDepthStencilState(&depthStencilDesc, &mCopyDepthStencilState);
- ASSERT(SUCCEEDED(result));
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal pixel transfer depth stencil state, result: 0x%X.", result);
- }
+ ANGLE_TRY(mRenderer->allocateResource(depthStencilDesc, &mCopyDepthStencilState));
D3D11_BUFFER_DESC constantBufferDesc = { 0 };
constantBufferDesc.ByteWidth = roundUp<UINT>(sizeof(CopyShaderParams), 32u);
@@ -120,38 +95,23 @@ gl::Error PixelTransfer11::loadResources()
constantBufferDesc.MiscFlags = 0;
constantBufferDesc.StructureByteStride = 0;
- result = device->CreateBuffer(&constantBufferDesc, NULL, &mParamsConstantBuffer);
- ASSERT(SUCCEEDED(result));
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal pixel transfer constant buffer, result: 0x%X.", result);
- }
- d3d11::SetDebugName(mParamsConstantBuffer, "PixelTransfer11 constant buffer");
+ ANGLE_TRY(mRenderer->allocateResource(constantBufferDesc, &mParamsConstantBuffer));
+ mParamsConstantBuffer.setDebugName("PixelTransfer11 constant buffer");
// init shaders
- mBufferToTextureVS = d3d11::CompileVS(device, g_VS_BufferToTexture, "BufferToTexture VS");
- if (!mBufferToTextureVS)
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal buffer to texture vertex shader.");
- }
+ ANGLE_TRY(mRenderer->allocateResource(ShaderData(g_VS_BufferToTexture), &mBufferToTextureVS));
+ mBufferToTextureVS.setDebugName("BufferToTexture VS");
- mBufferToTextureGS = d3d11::CompileGS(device, g_GS_BufferToTexture, "BufferToTexture GS");
- if (!mBufferToTextureGS)
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal buffer to texture geometry shader.");
- }
+ ANGLE_TRY(mRenderer->allocateResource(ShaderData(g_GS_BufferToTexture), &mBufferToTextureGS));
+ mBufferToTextureGS.setDebugName("BufferToTexture GS");
- gl::Error error = buildShaderMap();
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(buildShaderMap());
StructZero(&mParamsData);
mResourcesLoaded = true;
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
void PixelTransfer11::setBufferToTextureCopyParams(const gl::Box &destArea, const gl::Extents &destSize, GLenum internalFormat,
@@ -162,7 +122,7 @@ void PixelTransfer11::setBufferToTextureCopyParams(const gl::Box &destArea, cons
float texelCenterX = 0.5f / static_cast<float>(destSize.width - 1);
float texelCenterY = 0.5f / static_cast<float>(destSize.height - 1);
- unsigned int bytesPerPixel = gl::GetInternalFormatInfo(internalFormat).pixelBytes;
+ unsigned int bytesPerPixel = gl::GetSizedInternalFormatInfo(internalFormat).pixelBytes;
unsigned int alignmentBytes = static_cast<unsigned int>(unpack.alignment);
unsigned int alignmentPixels = (alignmentBytes <= bytesPerPixel ? 1 : alignmentBytes / bytesPerPixel);
@@ -177,14 +137,15 @@ void PixelTransfer11::setBufferToTextureCopyParams(const gl::Box &destArea, cons
parametersOut->FirstSlice = destArea.z;
}
-gl::Error PixelTransfer11::copyBufferToTexture(const gl::PixelUnpackState &unpack, unsigned int offset, RenderTargetD3D *destRenderTarget,
- GLenum destinationFormat, GLenum sourcePixelsType, const gl::Box &destArea)
+gl::Error PixelTransfer11::copyBufferToTexture(const gl::Context *context,
+ const gl::PixelUnpackState &unpack,
+ unsigned int offset,
+ RenderTargetD3D *destRenderTarget,
+ GLenum destinationFormat,
+ GLenum sourcePixelsType,
+ const gl::Box &destArea)
{
- gl::Error error = loadResources();
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(loadResources());
gl::Extents destSize = destRenderTarget->getExtents();
@@ -192,114 +153,106 @@ gl::Error PixelTransfer11::copyBufferToTexture(const gl::PixelUnpackState &unpac
destArea.y >= 0 && destArea.y + destArea.height <= destSize.height &&
destArea.z >= 0 && destArea.z + destArea.depth <= destSize.depth );
- const gl::Buffer &sourceBuffer = *unpack.pixelBuffer.get();
+ const gl::Buffer &sourceBuffer =
+ *context->getGLState().getTargetBuffer(gl::BufferBinding::PixelUnpack);
ASSERT(mRenderer->supportsFastCopyBufferToTexture(destinationFormat));
- ID3D11PixelShader *pixelShader = findBufferToTexturePS(destinationFormat);
+ const d3d11::PixelShader *pixelShader = findBufferToTexturePS(destinationFormat);
ASSERT(pixelShader);
// The SRV must be in the proper read format, which may be different from the destination format
// EG: for half float data, we can load full precision floats with implicit conversion
- GLenum unsizedFormat = gl::GetInternalFormatInfo(destinationFormat).format;
- GLenum sourceFormat = gl::GetSizedInternalFormat(unsizedFormat, sourcePixelsType);
+ GLenum unsizedFormat = gl::GetUnsizedFormat(destinationFormat);
+ const gl::InternalFormat &sourceglFormatInfo =
+ gl::GetInternalFormatInfo(unsizedFormat, sourcePixelsType);
- const d3d11::TextureFormat &sourceFormatInfo = d3d11::GetTextureFormatInfo(sourceFormat, mRenderer->getRenderer11DeviceCaps());
+ const d3d11::Format &sourceFormatInfo = d3d11::Format::Get(
+ sourceglFormatInfo.sizedInternalFormat, mRenderer->getRenderer11DeviceCaps());
DXGI_FORMAT srvFormat = sourceFormatInfo.srvFormat;
ASSERT(srvFormat != DXGI_FORMAT_UNKNOWN);
Buffer11 *bufferStorage11 = GetAs<Buffer11>(sourceBuffer.getImplementation());
- ID3D11ShaderResourceView *bufferSRV = bufferStorage11->getSRV(srvFormat);
- ASSERT(bufferSRV != NULL);
+ const d3d11::ShaderResourceView *bufferSRV = nullptr;
+ ANGLE_TRY_RESULT(bufferStorage11->getSRV(context, srvFormat), bufferSRV);
+ ASSERT(bufferSRV != nullptr);
- ID3D11RenderTargetView *textureRTV = GetAs<RenderTarget11>(destRenderTarget)->getRenderTargetView();
- ASSERT(textureRTV != NULL);
+ const d3d11::RenderTargetView &textureRTV =
+ GetAs<RenderTarget11>(destRenderTarget)->getRenderTargetView();
+ ASSERT(textureRTV.valid());
CopyShaderParams shaderParams;
- setBufferToTextureCopyParams(destArea, destSize, sourceFormat, unpack, offset, &shaderParams);
+ setBufferToTextureCopyParams(destArea, destSize, sourceglFormatInfo.sizedInternalFormat, unpack,
+ offset, &shaderParams);
ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
- ID3D11Buffer *nullBuffer = NULL;
- UINT zero = 0;
-
// Are we doing a 2D or 3D copy?
- ID3D11GeometryShader *geometryShader = ((destSize.depth > 1) ? mBufferToTextureGS : NULL);
- auto stateManager = mRenderer->getStateManager();
+ const auto *geometryShader = ((destSize.depth > 1) ? &mBufferToTextureGS : nullptr);
+ StateManager11 *stateManager = mRenderer->getStateManager();
- deviceContext->VSSetShader(mBufferToTextureVS, NULL, 0);
- deviceContext->GSSetShader(geometryShader, NULL, 0);
- deviceContext->PSSetShader(pixelShader, NULL, 0);
+ stateManager->setDrawShaders(&mBufferToTextureVS, geometryShader, pixelShader);
stateManager->setShaderResource(gl::SAMPLER_PIXEL, 0, bufferSRV);
- deviceContext->IASetInputLayout(NULL);
- deviceContext->IASetPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY_POINTLIST);
+ stateManager->setInputLayout(nullptr);
+ stateManager->setPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY_POINTLIST);
- deviceContext->IASetVertexBuffers(0, 1, &nullBuffer, &zero, &zero);
- deviceContext->OMSetBlendState(NULL, NULL, 0xFFFFFFF);
- deviceContext->OMSetDepthStencilState(mCopyDepthStencilState, 0xFFFFFFFF);
- deviceContext->RSSetState(mCopyRasterizerState);
+ stateManager->setSingleVertexBuffer(nullptr, 0, 0);
+ stateManager->setSimpleBlendState(nullptr);
+ stateManager->setDepthStencilState(&mCopyDepthStencilState, 0xFFFFFFFF);
+ stateManager->setRasterizerState(&mCopyRasterizerState);
- mRenderer->setOneTimeRenderTarget(textureRTV);
+ stateManager->setRenderTarget(textureRTV.get(), nullptr);
if (!StructEquals(mParamsData, shaderParams))
{
- d3d11::SetBufferData(deviceContext, mParamsConstantBuffer, shaderParams);
+ d3d11::SetBufferData(deviceContext, mParamsConstantBuffer.get(), shaderParams);
mParamsData = shaderParams;
}
- deviceContext->VSSetConstantBuffers(0, 1, &mParamsConstantBuffer);
+ stateManager->setVertexConstantBuffer(0, &mParamsConstantBuffer);
// Set the viewport
- D3D11_VIEWPORT viewport;
- viewport.TopLeftX = 0;
- viewport.TopLeftY = 0;
- viewport.Width = static_cast<FLOAT>(destSize.width);
- viewport.Height = static_cast<FLOAT>(destSize.height);
- viewport.MinDepth = 0.0f;
- viewport.MaxDepth = 1.0f;
- deviceContext->RSSetViewports(1, &viewport);
+ stateManager->setSimpleViewport(destSize);
UINT numPixels = (destArea.width * destArea.height * destArea.depth);
deviceContext->Draw(numPixels, 0);
- // Unbind textures and render targets and vertex buffer
- stateManager->setShaderResource(gl::SAMPLER_PIXEL, 0, NULL);
- deviceContext->VSSetConstantBuffers(0, 1, &nullBuffer);
-
- mRenderer->markAllStateDirty();
-
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
gl::Error PixelTransfer11::buildShaderMap()
{
- ID3D11Device *device = mRenderer->getDevice();
-
- mBufferToTexturePSMap[GL_FLOAT] = d3d11::CompilePS(device, g_PS_BufferToTexture_4F, "BufferToTexture RGBA ps");
- mBufferToTexturePSMap[GL_INT] = d3d11::CompilePS(device, g_PS_BufferToTexture_4I, "BufferToTexture RGBA-I ps");
- mBufferToTexturePSMap[GL_UNSIGNED_INT] = d3d11::CompilePS(device, g_PS_BufferToTexture_4UI, "BufferToTexture RGBA-UI ps");
-
- // Check that all the shaders were created successfully
- for (auto shaderMapIt = mBufferToTexturePSMap.begin(); shaderMapIt != mBufferToTexturePSMap.end(); shaderMapIt++)
- {
- if (shaderMapIt->second == NULL)
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal buffer to texture pixel shader.");
- }
- }
-
- return gl::Error(GL_NO_ERROR);
+ d3d11::PixelShader bufferToTextureFloat;
+ d3d11::PixelShader bufferToTextureInt;
+ d3d11::PixelShader bufferToTextureUint;
+
+ ANGLE_TRY(
+ mRenderer->allocateResource(ShaderData(g_PS_BufferToTexture_4F), &bufferToTextureFloat));
+ ANGLE_TRY(
+ mRenderer->allocateResource(ShaderData(g_PS_BufferToTexture_4I), &bufferToTextureInt));
+ ANGLE_TRY(
+ mRenderer->allocateResource(ShaderData(g_PS_BufferToTexture_4UI), &bufferToTextureUint));
+
+ bufferToTextureFloat.setDebugName("BufferToTexture RGBA ps");
+ bufferToTextureInt.setDebugName("BufferToTexture RGBA-I ps");
+ bufferToTextureUint.setDebugName("BufferToTexture RGBA-UI ps");
+
+ mBufferToTexturePSMap[GL_FLOAT] = std::move(bufferToTextureFloat);
+ mBufferToTexturePSMap[GL_INT] = std::move(bufferToTextureInt);
+ mBufferToTexturePSMap[GL_UNSIGNED_INT] = std::move(bufferToTextureUint);
+
+ return gl::NoError();
}
-ID3D11PixelShader *PixelTransfer11::findBufferToTexturePS(GLenum internalFormat) const
+const d3d11::PixelShader *PixelTransfer11::findBufferToTexturePS(GLenum internalFormat) const
{
- GLenum componentType = gl::GetInternalFormatInfo(internalFormat).componentType;
+ GLenum componentType = gl::GetSizedInternalFormatInfo(internalFormat).componentType;
if (componentType == GL_SIGNED_NORMALIZED || componentType == GL_UNSIGNED_NORMALIZED)
{
componentType = GL_FLOAT;
}
auto shaderMapIt = mBufferToTexturePSMap.find(componentType);
- return (shaderMapIt == mBufferToTexturePSMap.end() ? NULL : shaderMapIt->second);
+ return (shaderMapIt == mBufferToTexturePSMap.end() ? nullptr : &shaderMapIt->second);
}
-}
+} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/PixelTransfer11.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/PixelTransfer11.h
index 1672121ec7..a93544247e 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/PixelTransfer11.h
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/PixelTransfer11.h
@@ -11,14 +11,14 @@
#ifndef LIBANGLE_RENDERER_D3D_D3D11_PIXELTRANSFER11_H_
#define LIBANGLE_RENDERER_D3D_D3D11_PIXELTRANSFER11_H_
-#include "libANGLE/Error.h"
-
-#include "common/platform.h"
-
#include <GLES2/gl2.h>
#include <map>
+#include "common/platform.h"
+#include "libANGLE/Error.h"
+#include "libANGLE/renderer/d3d/d3d11/ResourceManager11.h"
+
namespace gl
{
@@ -45,8 +45,13 @@ class PixelTransfer11
// destRenderTarget: individual slice/layer of a target texture
// destinationFormat/sourcePixelsType: determines shaders + shader parameters
// destArea: the sub-section of destRenderTarget to copy to
- gl::Error copyBufferToTexture(const gl::PixelUnpackState &unpack, unsigned int offset, RenderTargetD3D *destRenderTarget,
- GLenum destinationFormat, GLenum sourcePixelsType, const gl::Box &destArea);
+ gl::Error copyBufferToTexture(const gl::Context *context,
+ const gl::PixelUnpackState &unpack,
+ unsigned int offset,
+ RenderTargetD3D *destRenderTarget,
+ GLenum destinationFormat,
+ GLenum sourcePixelsType,
+ const gl::Box &destArea);
private:
@@ -68,22 +73,21 @@ class PixelTransfer11
gl::Error loadResources();
gl::Error buildShaderMap();
- ID3D11PixelShader *findBufferToTexturePS(GLenum internalFormat) const;
+ const d3d11::PixelShader *findBufferToTexturePS(GLenum internalFormat) const;
Renderer11 *mRenderer;
bool mResourcesLoaded;
- std::map<GLenum, ID3D11PixelShader *> mBufferToTexturePSMap;
- ID3D11VertexShader *mBufferToTextureVS;
- ID3D11GeometryShader *mBufferToTextureGS;
- ID3D11Buffer *mParamsConstantBuffer;
+ std::map<GLenum, d3d11::PixelShader> mBufferToTexturePSMap;
+ d3d11::VertexShader mBufferToTextureVS;
+ d3d11::GeometryShader mBufferToTextureGS;
+ d3d11::Buffer mParamsConstantBuffer;
CopyShaderParams mParamsData;
- ID3D11RasterizerState *mCopyRasterizerState;
- ID3D11DepthStencilState *mCopyDepthStencilState;
-
+ d3d11::RasterizerState mCopyRasterizerState;
+ d3d11::DepthStencilState mCopyDepthStencilState;
};
-}
+} // namespace rx
#endif // LIBANGLE_RENDERER_D3D_D3D11_PIXELTRANSFER11_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/ProgramPipeline11.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/ProgramPipeline11.cpp
new file mode 100644
index 0000000000..c9554431e5
--- /dev/null
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/ProgramPipeline11.cpp
@@ -0,0 +1,24 @@
+//
+// Copyright 2017 The ANGLE Project Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+//
+// ProgramPipelineNULL.cpp:
+// Implements the class methods for ProgramPipeline11.
+//
+
+#include "libANGLE/renderer/d3d/d3d11/ProgramPipeline11.h"
+
+namespace rx
+{
+
+ProgramPipeline11::ProgramPipeline11(const gl::ProgramPipelineState &state)
+ : ProgramPipelineImpl(state)
+{
+}
+
+ProgramPipeline11::~ProgramPipeline11()
+{
+}
+
+} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/ProgramPipeline11.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/ProgramPipeline11.h
new file mode 100644
index 0000000000..cf838eec05
--- /dev/null
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/ProgramPipeline11.h
@@ -0,0 +1,27 @@
+//
+// Copyright 2017 The ANGLE Project Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+//
+// ProgramPipeline11.h:
+// Defines the class interface for ProgramPipeline11, implementing ProgramPipelineImpl.
+//
+
+#ifndef LIBANGLE_RENDERER_D3D_D3D11_PROGRAMPIPELINE11_H_
+#define LIBANGLE_RENDERER_D3D_D3D11_PROGRAMPIPELINE11_H_
+
+#include "libANGLE/renderer/ProgramPipelineImpl.h"
+
+namespace rx
+{
+
+class ProgramPipeline11 : public ProgramPipelineImpl
+{
+ public:
+ ProgramPipeline11(const gl::ProgramPipelineState &state);
+ ~ProgramPipeline11() override;
+};
+
+} // namespace rx
+
+#endif // LIBANGLE_RENDERER_D3D_D3D11_PROGRAMPIPELINE11_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Query11.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Query11.cpp
index 0a79b26df0..66b9476e7f 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Query11.cpp
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Query11.cpp
@@ -7,146 +7,96 @@
// Query11.cpp: Defines the rx::Query11 class which implements rx::QueryImpl.
#include "libANGLE/renderer/d3d/d3d11/Query11.h"
-#include "libANGLE/renderer/d3d/d3d11/Renderer11.h"
-#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
-#include "common/utilities.h"
#include <GLES2/gl2ext.h>
-#if defined(ANGLE_MINGW32_COMPAT)
-typedef struct D3D11_QUERY_DATA_SO_STATISTICS {
- UINT64 NumPrimitivesWritten;
- UINT64 PrimitivesStorageNeeded;
-} D3D11_QUERY_DATA_SO_STATISTICS;
-#endif // ANGLE_MINGW32_COMPAT
-
-#ifndef ANGLE_D3D11_QDTD_AVAILABLE
-typedef struct D3D11_QUERY_DATA_TIMESTAMP_DISJOINT {
- UINT64 Frequency;
- BOOL Disjoint;
-} D3D11_QUERY_DATA_TIMESTAMP_DISJOINT;
-#endif // MINGW32
+#include "common/utilities.h"
+#include "libANGLE/renderer/d3d/d3d11/Renderer11.h"
+#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
-namespace rx
+namespace
{
-Query11::Query11(Renderer11 *renderer, GLenum type)
- : QueryImpl(type),
- mResult(0),
- mQueryFinished(false),
- mRenderer(renderer),
- mQuery(nullptr),
- mTimestampBeginQuery(nullptr),
- mTimestampEndQuery(nullptr)
+GLuint64 MergeQueryResults(GLenum type, GLuint64 currentResult, GLuint64 newResult)
{
-}
+ switch (type)
+ {
+ case GL_ANY_SAMPLES_PASSED:
+ case GL_ANY_SAMPLES_PASSED_CONSERVATIVE:
+ return (currentResult == GL_TRUE || newResult == GL_TRUE) ? GL_TRUE : GL_FALSE;
-Query11::~Query11()
-{
- SafeRelease(mQuery);
- SafeRelease(mTimestampBeginQuery);
- SafeRelease(mTimestampEndQuery);
-}
+ case GL_TRANSFORM_FEEDBACK_PRIMITIVES_WRITTEN:
+ return currentResult + newResult;
-gl::Error Query11::begin()
-{
- if (mQuery == nullptr)
- {
- D3D11_QUERY_DESC queryDesc;
- queryDesc.Query = gl_d3d11::ConvertQueryType(getType());
- queryDesc.MiscFlags = 0;
+ case GL_TIME_ELAPSED_EXT:
+ return currentResult + newResult;
- ID3D11Device *device = mRenderer->getDevice();
+ case GL_TIMESTAMP_EXT:
+ return newResult;
- HRESULT result = device->CreateQuery(&queryDesc, &mQuery);
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Internal query creation failed, result: 0x%X.", result);
- }
+ case GL_COMMANDS_COMPLETED_CHROMIUM:
+ return newResult;
- // If we are doing time elapsed we also need a query to actually query the timestamp
- if (getType() == GL_TIME_ELAPSED_EXT)
- {
- D3D11_QUERY_DESC desc;
- desc.Query = D3D11_QUERY_TIMESTAMP;
- desc.MiscFlags = 0;
- result = device->CreateQuery(&desc, &mTimestampBeginQuery);
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Internal query creation failed, result: 0x%X.",
- result);
- }
- result = device->CreateQuery(&desc, &mTimestampEndQuery);
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Internal query creation failed, result: 0x%X.",
- result);
- }
- }
+ default:
+ UNREACHABLE();
+ return 0;
}
+}
- ID3D11DeviceContext *context = mRenderer->getDeviceContext();
+} // anonymous namespace
- context->Begin(mQuery);
+namespace rx
+{
- // If we are doing time elapsed query the begin timestamp
- if (getType() == GL_TIME_ELAPSED_EXT)
- {
- context->End(mTimestampBeginQuery);
- }
- return gl::Error(GL_NO_ERROR);
+Query11::QueryState::QueryState() : query(), beginTimestamp(), endTimestamp(), finished(false)
+{
}
-gl::Error Query11::end()
+Query11::QueryState::~QueryState()
{
- ASSERT(mQuery);
-
- ID3D11DeviceContext *context = mRenderer->getDeviceContext();
+}
- // If we are doing time elapsed query the end timestamp
- if (getType() == GL_TIME_ELAPSED_EXT)
- {
- context->End(mTimestampEndQuery);
- }
+Query11::Query11(Renderer11 *renderer, GLenum type)
+ : QueryImpl(type), mResult(0), mResultSum(0), mRenderer(renderer)
+{
+ mActiveQuery = std::unique_ptr<QueryState>(new QueryState());
+}
- context->End(mQuery);
+Query11::~Query11()
+{
+ mRenderer->getStateManager()->onDeleteQueryObject(this);
+}
- mQueryFinished = false;
- mResult = GL_FALSE;
+gl::Error Query11::begin()
+{
+ mResultSum = 0;
+ mRenderer->getStateManager()->onBeginQuery(this);
+ return resume();
+}
- return gl::Error(GL_NO_ERROR);
+gl::Error Query11::end()
+{
+ return pause();
}
gl::Error Query11::queryCounter()
{
// This doesn't do anything for D3D11 as we don't support timestamps
ASSERT(getType() == GL_TIMESTAMP_EXT);
- mQueryFinished = true;
- mResult = 0;
- return gl::Error(GL_NO_ERROR);
+ mResultSum = 0;
+ mPendingQueries.push_back(std::unique_ptr<QueryState>(new QueryState()));
+ return gl::NoError();
}
template <typename T>
gl::Error Query11::getResultBase(T *params)
{
- while (!mQueryFinished)
- {
- gl::Error error = testQuery();
- if (error.isError())
- {
- return error;
- }
-
- if (!mQueryFinished)
- {
- ScheduleYield();
- }
- }
+ ASSERT(!mActiveQuery->query.valid());
+ ANGLE_TRY(flush(true));
+ ASSERT(mPendingQueries.empty());
+ *params = static_cast<T>(mResultSum);
- ASSERT(mQueryFinished);
- *params = static_cast<T>(mResult);
-
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
gl::Error Query11::getResult(GLint *params)
@@ -171,105 +121,197 @@ gl::Error Query11::getResult(GLuint64 *params)
gl::Error Query11::isResultAvailable(bool *available)
{
- gl::Error error = testQuery();
- if (error.isError())
+ ANGLE_TRY(flush(false));
+
+ *available = mPendingQueries.empty();
+ return gl::NoError();
+}
+
+gl::Error Query11::pause()
+{
+ if (mActiveQuery->query.valid())
{
- return error;
+ ID3D11DeviceContext *context = mRenderer->getDeviceContext();
+ GLenum queryType = getType();
+
+ // If we are doing time elapsed query the end timestamp
+ if (queryType == GL_TIME_ELAPSED_EXT)
+ {
+ context->End(mActiveQuery->endTimestamp.get());
+ }
+
+ context->End(mActiveQuery->query.get());
+
+ mPendingQueries.push_back(std::move(mActiveQuery));
+ mActiveQuery = std::unique_ptr<QueryState>(new QueryState());
}
- *available = mQueryFinished;
+ return flush(false);
+}
+
+gl::Error Query11::resume()
+{
+ if (!mActiveQuery->query.valid())
+ {
+ ANGLE_TRY(flush(false));
+
+ GLenum queryType = getType();
+ D3D11_QUERY d3dQueryType = gl_d3d11::ConvertQueryType(queryType);
- return gl::Error(GL_NO_ERROR);
+ D3D11_QUERY_DESC queryDesc;
+ queryDesc.Query = d3dQueryType;
+ queryDesc.MiscFlags = 0;
+
+ ANGLE_TRY(mRenderer->allocateResource(queryDesc, &mActiveQuery->query));
+
+ // If we are doing time elapsed we also need a query to actually query the timestamp
+ if (queryType == GL_TIME_ELAPSED_EXT)
+ {
+ D3D11_QUERY_DESC desc;
+ desc.Query = D3D11_QUERY_TIMESTAMP;
+ desc.MiscFlags = 0;
+
+ ANGLE_TRY(mRenderer->allocateResource(desc, &mActiveQuery->beginTimestamp));
+ ANGLE_TRY(mRenderer->allocateResource(desc, &mActiveQuery->endTimestamp));
+ }
+
+ ID3D11DeviceContext *context = mRenderer->getDeviceContext();
+
+ if (d3dQueryType != D3D11_QUERY_EVENT)
+ {
+ context->Begin(mActiveQuery->query.get());
+ }
+
+ // If we are doing time elapsed, query the begin timestamp
+ if (queryType == GL_TIME_ELAPSED_EXT)
+ {
+ context->End(mActiveQuery->beginTimestamp.get());
+ }
+ }
+
+ return gl::NoError();
}
-gl::Error Query11::testQuery()
+gl::Error Query11::flush(bool force)
{
- if (!mQueryFinished)
+ while (!mPendingQueries.empty())
{
- ASSERT(mQuery);
+ QueryState *query = mPendingQueries.front().get();
+ do
+ {
+ ANGLE_TRY(testQuery(query));
+ if (!query->finished && !force)
+ {
+ return gl::NoError();
+ }
+ } while (!query->finished);
+
+ mResultSum = MergeQueryResults(getType(), mResultSum, mResult);
+ mPendingQueries.pop_front();
+ }
+
+ return gl::NoError();
+}
+
+gl::Error Query11::testQuery(QueryState *queryState)
+{
+ if (!queryState->finished)
+ {
ID3D11DeviceContext *context = mRenderer->getDeviceContext();
switch (getType())
{
- case GL_ANY_SAMPLES_PASSED_EXT:
- case GL_ANY_SAMPLES_PASSED_CONSERVATIVE_EXT:
+ case GL_ANY_SAMPLES_PASSED_EXT:
+ case GL_ANY_SAMPLES_PASSED_CONSERVATIVE_EXT:
{
+ ASSERT(queryState->query.valid());
UINT64 numPixels = 0;
- HRESULT result = context->GetData(mQuery, &numPixels, sizeof(numPixels), 0);
+ HRESULT result =
+ context->GetData(queryState->query.get(), &numPixels, sizeof(numPixels), 0);
if (FAILED(result))
{
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to get the data of an internal query, result: 0x%X.", result);
+ return gl::OutOfMemory()
+ << "Failed to get the data of an internal query, " << gl::FmtHR(result);
}
if (result == S_OK)
{
- mQueryFinished = true;
- mResult = (numPixels > 0) ? GL_TRUE : GL_FALSE;
+ queryState->finished = true;
+ mResult = (numPixels > 0) ? GL_TRUE : GL_FALSE;
}
}
break;
- case GL_TRANSFORM_FEEDBACK_PRIMITIVES_WRITTEN:
+ case GL_TRANSFORM_FEEDBACK_PRIMITIVES_WRITTEN:
{
- D3D11_QUERY_DATA_SO_STATISTICS soStats = { 0 };
- HRESULT result = context->GetData(mQuery, &soStats, sizeof(soStats), 0);
+ ASSERT(queryState->query.valid());
+ D3D11_QUERY_DATA_SO_STATISTICS soStats = {0};
+ HRESULT result =
+ context->GetData(queryState->query.get(), &soStats, sizeof(soStats), 0);
if (FAILED(result))
{
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to get the data of an internal query, result: 0x%X.", result);
+ return gl::OutOfMemory()
+ << "Failed to get the data of an internal query, " << gl::FmtHR(result);
}
if (result == S_OK)
{
- mQueryFinished = true;
- mResult = static_cast<GLuint64>(soStats.NumPrimitivesWritten);
+ queryState->finished = true;
+ mResult = static_cast<GLuint64>(soStats.NumPrimitivesWritten);
}
}
break;
case GL_TIME_ELAPSED_EXT:
{
+ ASSERT(queryState->query.valid());
+ ASSERT(queryState->beginTimestamp.valid());
+ ASSERT(queryState->endTimestamp.valid());
D3D11_QUERY_DATA_TIMESTAMP_DISJOINT timeStats = {0};
- HRESULT result = context->GetData(mQuery, &timeStats, sizeof(timeStats), 0);
+ HRESULT result =
+ context->GetData(queryState->query.get(), &timeStats, sizeof(timeStats), 0);
if (FAILED(result))
{
- return gl::Error(GL_OUT_OF_MEMORY,
- "Failed to get the data of an internal query, result: 0x%X.",
- result);
+ return gl::OutOfMemory()
+ << "Failed to get the data of an internal query, " << gl::FmtHR(result);
}
if (result == S_OK)
{
UINT64 beginTime = 0;
- HRESULT beginRes =
- context->GetData(mTimestampBeginQuery, &beginTime, sizeof(UINT64), 0);
+ HRESULT beginRes = context->GetData(queryState->beginTimestamp.get(),
+ &beginTime, sizeof(UINT64), 0);
if (FAILED(beginRes))
{
- return gl::Error(
- GL_OUT_OF_MEMORY,
- "Failed to get the data of an internal query, result: 0x%X.", beginRes);
+ return gl::OutOfMemory() << "Failed to get the data of an internal query, "
+ << gl::FmtHR(beginRes);
}
UINT64 endTime = 0;
- HRESULT endRes =
- context->GetData(mTimestampEndQuery, &endTime, sizeof(UINT64), 0);
+ HRESULT endRes = context->GetData(queryState->endTimestamp.get(), &endTime,
+ sizeof(UINT64), 0);
if (FAILED(endRes))
{
- return gl::Error(
- GL_OUT_OF_MEMORY,
- "Failed to get the data of an internal query, result: 0x%X.", endRes);
+ return gl::OutOfMemory() << "Failed to get the data of an internal query, "
+ << gl::FmtHR(endRes);
}
if (beginRes == S_OK && endRes == S_OK)
{
- mQueryFinished = true;
+ queryState->finished = true;
if (timeStats.Disjoint)
{
mRenderer->setGPUDisjoint();
}
static_assert(sizeof(UINT64) == sizeof(unsigned long long),
"D3D UINT64 isn't 64 bits");
- if (rx::IsUnsignedMultiplicationSafe(endTime - beginTime, 1000000000ull))
+
+ angle::CheckedNumeric<UINT64> checkedTime(endTime);
+ checkedTime -= beginTime;
+ checkedTime *= 1000000000ull;
+ checkedTime /= timeStats.Frequency;
+ if (checkedTime.IsValid())
{
- mResult = ((endTime - beginTime) * 1000000000ull) / timeStats.Frequency;
+ mResult = checkedTime.ValueOrDie();
}
else
{
@@ -288,23 +330,46 @@ gl::Error Query11::testQuery()
// D3D11 doesn't support GL timestamp queries as D3D timestamps are not guaranteed
// to have any sort of continuity outside of a disjoint timestamp query block, which
// GL depends on
- mResult = 0;
+ ASSERT(!queryState->query.valid());
+ mResult = 0;
+ queryState->finished = true;
}
break;
- default:
- UNREACHABLE();
+ case GL_COMMANDS_COMPLETED_CHROMIUM:
+ {
+ ASSERT(queryState->query.valid());
+ BOOL completed = 0;
+ HRESULT result =
+ context->GetData(queryState->query.get(), &completed, sizeof(completed), 0);
+ if (FAILED(result))
+ {
+ return gl::OutOfMemory()
+ << "Failed to get the data of an internal query, " << gl::FmtHR(result);
+ }
+
+ if (result == S_OK)
+ {
+ queryState->finished = true;
+ ASSERT(completed == TRUE);
+ mResult = (completed == TRUE) ? GL_TRUE : GL_FALSE;
+ }
+ }
break;
+
+ default:
+ UNREACHABLE();
+ break;
}
- if (!mQueryFinished && mRenderer->testDeviceLost())
+ if (!queryState->finished && mRenderer->testDeviceLost())
{
mRenderer->notifyDeviceLost();
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to test get query result, device is lost.");
+ return gl::OutOfMemory() << "Failed to test get query result, device is lost.";
}
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-}
+} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Query11.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Query11.h
index 29a6e6f85d..a88a8892aa 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Query11.h
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Query11.h
@@ -9,7 +9,10 @@
#ifndef LIBANGLE_RENDERER_D3D_D3D11_QUERY11_H_
#define LIBANGLE_RENDERER_D3D_D3D11_QUERY11_H_
+#include <deque>
+
#include "libANGLE/renderer/QueryImpl.h"
+#include "libANGLE/renderer/d3d/d3d11/ResourceManager11.h"
namespace rx
{
@@ -19,31 +22,45 @@ class Query11 : public QueryImpl
{
public:
Query11(Renderer11 *renderer, GLenum type);
- virtual ~Query11();
+ ~Query11() override;
+
+ gl::Error begin() override;
+ gl::Error end() override;
+ gl::Error queryCounter() override;
+ gl::Error getResult(GLint *params) override;
+ gl::Error getResult(GLuint *params) override;
+ gl::Error getResult(GLint64 *params) override;
+ gl::Error getResult(GLuint64 *params) override;
+ gl::Error isResultAvailable(bool *available) override;
- virtual gl::Error begin();
- virtual gl::Error end();
- virtual gl::Error queryCounter();
- virtual gl::Error getResult(GLint *params);
- virtual gl::Error getResult(GLuint *params);
- virtual gl::Error getResult(GLint64 *params);
- virtual gl::Error getResult(GLuint64 *params);
- virtual gl::Error isResultAvailable(bool *available);
+ gl::Error pause();
+ gl::Error resume();
private:
- gl::Error testQuery();
+ struct QueryState final : private angle::NonCopyable
+ {
+ QueryState();
+ ~QueryState();
+
+ d3d11::Query query;
+ d3d11::Query beginTimestamp;
+ d3d11::Query endTimestamp;
+ bool finished;
+ };
+
+ gl::Error flush(bool force);
+ gl::Error testQuery(QueryState *queryState);
template <typename T>
gl::Error getResultBase(T *params);
GLuint64 mResult;
-
- bool mQueryFinished;
+ GLuint64 mResultSum;
Renderer11 *mRenderer;
- ID3D11Query *mQuery;
- ID3D11Query *mTimestampBeginQuery;
- ID3D11Query *mTimestampEndQuery;
+
+ std::unique_ptr<QueryState> mActiveQuery;
+ std::deque<std::unique_ptr<QueryState>> mPendingQueries;
};
}
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/RenderStateCache.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/RenderStateCache.cpp
index 2ee25cfb6c..5b85196c2e 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/RenderStateCache.cpp
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/RenderStateCache.cpp
@@ -17,338 +17,180 @@
#include "libANGLE/renderer/d3d/FramebufferD3D.h"
#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
#include "libANGLE/renderer/d3d/d3d11/Renderer11.h"
-#include "third_party/murmurhash/MurmurHash3.h"
namespace rx
{
using namespace gl_d3d11;
-template <typename mapType>
-static void ClearStateMap(mapType &map)
-{
- for (typename mapType::iterator i = map.begin(); i != map.end(); i++)
- {
- SafeRelease(i->second.first);
- }
- map.clear();
-}
-
-// MSDN's documentation of ID3D11Device::CreateBlendState, ID3D11Device::CreateRasterizerState,
-// ID3D11Device::CreateDepthStencilState and ID3D11Device::CreateSamplerState claims the maximum
-// number of unique states of each type an application can create is 4096
-const unsigned int RenderStateCache::kMaxBlendStates = 4096;
-const unsigned int RenderStateCache::kMaxRasterizerStates = 4096;
-const unsigned int RenderStateCache::kMaxDepthStencilStates = 4096;
-const unsigned int RenderStateCache::kMaxSamplerStates = 4096;
-
-RenderStateCache::RenderStateCache(Renderer11 *renderer)
- : mRenderer(renderer),
- mCounter(0),
- mBlendStateCache(kMaxBlendStates, hashBlendState, compareBlendStates),
- mRasterizerStateCache(kMaxRasterizerStates, hashRasterizerState, compareRasterizerStates),
- mDepthStencilStateCache(kMaxDepthStencilStates, hashDepthStencilState, compareDepthStencilStates),
- mSamplerStateCache(kMaxSamplerStates, hashSamplerState, compareSamplerStates),
- mDevice(NULL)
+RenderStateCache::RenderStateCache()
+ : mBlendStateCache(kMaxStates),
+ mRasterizerStateCache(kMaxStates),
+ mDepthStencilStateCache(kMaxStates),
+ mSamplerStateCache(kMaxStates)
{
}
RenderStateCache::~RenderStateCache()
{
- clear();
-}
-
-void RenderStateCache::initialize(ID3D11Device *device)
-{
- clear();
- mDevice = device;
}
void RenderStateCache::clear()
{
- ClearStateMap(mBlendStateCache);
- ClearStateMap(mRasterizerStateCache);
- ClearStateMap(mDepthStencilStateCache);
- ClearStateMap(mSamplerStateCache);
+ mBlendStateCache.Clear();
+ mRasterizerStateCache.Clear();
+ mDepthStencilStateCache.Clear();
+ mSamplerStateCache.Clear();
}
-std::size_t RenderStateCache::hashBlendState(const BlendStateKey &blendState)
+// static
+d3d11::BlendStateKey RenderStateCache::GetBlendStateKey(const gl::Context *context,
+ const gl::Framebuffer *framebuffer,
+ const gl::BlendState &blendState)
{
- static const unsigned int seed = 0xABCDEF98;
-
- std::size_t hash = 0;
- MurmurHash3_x86_32(&blendState, sizeof(gl::BlendState), seed, &hash);
- return hash;
-}
+ d3d11::BlendStateKey key;
+ FramebufferD3D *framebufferD3D = GetImplAs<FramebufferD3D>(framebuffer);
+ const gl::AttachmentList &colorbuffers = framebufferD3D->getColorAttachmentsForRender(context);
+ const UINT8 blendStateMask =
+ gl_d3d11::ConvertColorMask(blendState.colorMaskRed, blendState.colorMaskGreen,
+ blendState.colorMaskBlue, blendState.colorMaskAlpha);
-bool RenderStateCache::compareBlendStates(const BlendStateKey &a, const BlendStateKey &b)
-{
- return memcmp(&a, &b, sizeof(BlendStateKey)) == 0;
-}
-
-gl::Error RenderStateCache::getBlendState(const gl::Framebuffer *framebuffer, const gl::BlendState &blendState,
- ID3D11BlendState **outBlendState)
-{
- if (!mDevice)
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Internal error, RenderStateCache is not initialized.");
- }
-
- bool mrt = false;
-
- const FramebufferD3D *framebufferD3D = GetImplAs<FramebufferD3D>(framebuffer);
- const gl::AttachmentList &colorbuffers = framebufferD3D->getColorAttachmentsForRender();
-
- BlendStateKey key = {};
key.blendState = blendState;
- for (size_t colorAttachment = 0; colorAttachment < colorbuffers.size(); ++colorAttachment)
- {
- const gl::FramebufferAttachment *attachment = colorbuffers[colorAttachment];
- auto rtChannels = key.rtChannels[colorAttachment];
+ for (size_t i = 0; i < colorbuffers.size(); i++)
+ {
+ const gl::FramebufferAttachment *attachment = colorbuffers[i];
if (attachment)
{
- if (colorAttachment > 0)
- {
- mrt = true;
- }
-
- rtChannels[0] = attachment->getRedSize() > 0;
- rtChannels[1] = attachment->getGreenSize() > 0;
- rtChannels[2] = attachment->getBlueSize() > 0;
- rtChannels[3] = attachment->getAlphaSize() > 0;
+ key.rtvMax = static_cast<uint32_t>(i) + 1;
+ key.rtvMasks[i] =
+ (gl_d3d11::GetColorMask(*attachment->getFormat().info)) & blendStateMask;
}
}
- BlendStateMap::iterator keyIter = mBlendStateCache.find(key);
+ return key;
+}
+
+gl::Error RenderStateCache::getBlendState(Renderer11 *renderer,
+ const d3d11::BlendStateKey &key,
+ const d3d11::BlendState **outBlendState)
+{
+ auto keyIter = mBlendStateCache.Get(key);
if (keyIter != mBlendStateCache.end())
{
- BlendStateCounterPair &state = keyIter->second;
- state.second = mCounter++;
- *outBlendState = state.first;
- return gl::Error(GL_NO_ERROR);
+ *outBlendState = &keyIter->second;
+ return gl::NoError();
}
- else
- {
- if (mBlendStateCache.size() >= kMaxBlendStates)
- {
- TRACE("Overflowed the limit of %u blend states, removing the least recently used "
- "to make room.", kMaxBlendStates);
-
- BlendStateMap::iterator leastRecentlyUsed = mBlendStateCache.begin();
- for (BlendStateMap::iterator i = mBlendStateCache.begin(); i != mBlendStateCache.end(); i++)
- {
- if (i->second.second < leastRecentlyUsed->second.second)
- {
- leastRecentlyUsed = i;
- }
- }
- SafeRelease(leastRecentlyUsed->second.first);
- mBlendStateCache.erase(leastRecentlyUsed);
- }
- // Create a new blend state and insert it into the cache
- D3D11_BLEND_DESC blendDesc = { 0 };
- blendDesc.AlphaToCoverageEnable = blendState.sampleAlphaToCoverage;
- blendDesc.IndependentBlendEnable = mrt ? TRUE : FALSE;
+ TrimCache(kMaxStates, kGCLimit, "blend state", &mBlendStateCache);
- for (unsigned int i = 0; i < D3D11_SIMULTANEOUS_RENDER_TARGET_COUNT; i++)
- {
- D3D11_RENDER_TARGET_BLEND_DESC &rtBlend = blendDesc.RenderTarget[i];
-
- rtBlend.BlendEnable = blendState.blend;
- if (blendState.blend)
- {
- rtBlend.SrcBlend = gl_d3d11::ConvertBlendFunc(blendState.sourceBlendRGB, false);
- rtBlend.DestBlend = gl_d3d11::ConvertBlendFunc(blendState.destBlendRGB, false);
- rtBlend.BlendOp = gl_d3d11::ConvertBlendOp(blendState.blendEquationRGB);
-
- rtBlend.SrcBlendAlpha = gl_d3d11::ConvertBlendFunc(blendState.sourceBlendAlpha, true);
- rtBlend.DestBlendAlpha = gl_d3d11::ConvertBlendFunc(blendState.destBlendAlpha, true);
- rtBlend.BlendOpAlpha = gl_d3d11::ConvertBlendOp(blendState.blendEquationAlpha);
- }
-
- rtBlend.RenderTargetWriteMask = gl_d3d11::ConvertColorMask(key.rtChannels[i][0] && blendState.colorMaskRed,
- key.rtChannels[i][1] && blendState.colorMaskGreen,
- key.rtChannels[i][2] && blendState.colorMaskBlue,
- key.rtChannels[i][3] && blendState.colorMaskAlpha);
- }
+ // Create a new blend state and insert it into the cache
+ D3D11_BLEND_DESC blendDesc;
+ D3D11_RENDER_TARGET_BLEND_DESC &rtDesc0 = blendDesc.RenderTarget[0];
+ const gl::BlendState &blendState = key.blendState;
- ID3D11BlendState *dx11BlendState = NULL;
- HRESULT result = mDevice->CreateBlendState(&blendDesc, &dx11BlendState);
- if (FAILED(result) || !dx11BlendState)
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Unable to create a ID3D11BlendState, HRESULT: 0x%X.", result);
- }
+ blendDesc.AlphaToCoverageEnable = blendState.sampleAlphaToCoverage;
+ blendDesc.IndependentBlendEnable = key.rtvMax > 1 ? TRUE : FALSE;
- mBlendStateCache.insert(std::make_pair(key, std::make_pair(dx11BlendState, mCounter++)));
+ rtDesc0 = {};
- *outBlendState = dx11BlendState;
- return gl::Error(GL_NO_ERROR);
+ if (blendState.blend)
+ {
+ rtDesc0.BlendEnable = true;
+ rtDesc0.SrcBlend = gl_d3d11::ConvertBlendFunc(blendState.sourceBlendRGB, false);
+ rtDesc0.DestBlend = gl_d3d11::ConvertBlendFunc(blendState.destBlendRGB, false);
+ rtDesc0.BlendOp = gl_d3d11::ConvertBlendOp(blendState.blendEquationRGB);
+ rtDesc0.SrcBlendAlpha = gl_d3d11::ConvertBlendFunc(blendState.sourceBlendAlpha, true);
+ rtDesc0.DestBlendAlpha = gl_d3d11::ConvertBlendFunc(blendState.destBlendAlpha, true);
+ rtDesc0.BlendOpAlpha = gl_d3d11::ConvertBlendOp(blendState.blendEquationAlpha);
}
-}
-std::size_t RenderStateCache::hashRasterizerState(const RasterizerStateKey &rasterState)
-{
- static const unsigned int seed = 0xABCDEF98;
+ rtDesc0.RenderTargetWriteMask = key.rtvMasks[0];
- std::size_t hash = 0;
- MurmurHash3_x86_32(&rasterState, sizeof(RasterizerStateKey), seed, &hash);
- return hash;
-}
+ for (unsigned int i = 1; i < D3D11_SIMULTANEOUS_RENDER_TARGET_COUNT; i++)
+ {
+ blendDesc.RenderTarget[i] = rtDesc0;
+ blendDesc.RenderTarget[i].RenderTargetWriteMask = key.rtvMasks[i];
+ }
-bool RenderStateCache::compareRasterizerStates(const RasterizerStateKey &a, const RasterizerStateKey &b)
-{
- return memcmp(&a, &b, sizeof(RasterizerStateKey)) == 0;
+ d3d11::BlendState d3dBlendState;
+ ANGLE_TRY(renderer->allocateResource(blendDesc, &d3dBlendState));
+ const auto &iter = mBlendStateCache.Put(key, std::move(d3dBlendState));
+
+ *outBlendState = &iter->second;
+
+ return gl::NoError();
}
-gl::Error RenderStateCache::getRasterizerState(const gl::RasterizerState &rasterState, bool scissorEnabled,
+gl::Error RenderStateCache::getRasterizerState(Renderer11 *renderer,
+ const gl::RasterizerState &rasterState,
+ bool scissorEnabled,
ID3D11RasterizerState **outRasterizerState)
{
- if (!mDevice)
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Internal error, RenderStateCache is not initialized.");
- }
-
- RasterizerStateKey key = {};
+ d3d11::RasterizerStateKey key;
key.rasterizerState = rasterState;
- key.scissorEnabled = scissorEnabled;
+ key.scissorEnabled = scissorEnabled ? 1 : 0;
- RasterizerStateMap::iterator keyIter = mRasterizerStateCache.find(key);
+ auto keyIter = mRasterizerStateCache.Get(key);
if (keyIter != mRasterizerStateCache.end())
{
- RasterizerStateCounterPair &state = keyIter->second;
- state.second = mCounter++;
- *outRasterizerState = state.first;
- return gl::Error(GL_NO_ERROR);
+ *outRasterizerState = keyIter->second.get();
+ return gl::NoError();
}
- else
- {
- if (mRasterizerStateCache.size() >= kMaxRasterizerStates)
- {
- TRACE("Overflowed the limit of %u rasterizer states, removing the least recently used "
- "to make room.", kMaxRasterizerStates);
-
- RasterizerStateMap::iterator leastRecentlyUsed = mRasterizerStateCache.begin();
- for (RasterizerStateMap::iterator i = mRasterizerStateCache.begin(); i != mRasterizerStateCache.end(); i++)
- {
- if (i->second.second < leastRecentlyUsed->second.second)
- {
- leastRecentlyUsed = i;
- }
- }
- SafeRelease(leastRecentlyUsed->second.first);
- mRasterizerStateCache.erase(leastRecentlyUsed);
- }
- D3D11_CULL_MODE cullMode = gl_d3d11::ConvertCullMode(rasterState.cullFace, rasterState.cullMode);
+ TrimCache(kMaxStates, kGCLimit, "rasterizer state", &mRasterizerStateCache);
- // Disable culling if drawing points
- if (rasterState.pointDrawMode)
- {
- cullMode = D3D11_CULL_NONE;
- }
+ D3D11_CULL_MODE cullMode =
+ gl_d3d11::ConvertCullMode(rasterState.cullFace, rasterState.cullMode);
- D3D11_RASTERIZER_DESC rasterDesc;
- rasterDesc.FillMode = D3D11_FILL_SOLID;
- rasterDesc.CullMode = cullMode;
- rasterDesc.FrontCounterClockwise = (rasterState.frontFace == GL_CCW) ? FALSE: TRUE;
- rasterDesc.DepthBiasClamp = 0.0f; // MSDN documentation of DepthBiasClamp implies a value of zero will preform no clamping, must be tested though.
- rasterDesc.DepthClipEnable = TRUE;
- rasterDesc.ScissorEnable = scissorEnabled ? TRUE : FALSE;
- rasterDesc.MultisampleEnable = rasterState.multiSample;
- rasterDesc.AntialiasedLineEnable = FALSE;
-
- if (rasterState.polygonOffsetFill)
- {
- rasterDesc.SlopeScaledDepthBias = rasterState.polygonOffsetFactor;
- rasterDesc.DepthBias = (INT)rasterState.polygonOffsetUnits;
- }
- else
- {
- rasterDesc.SlopeScaledDepthBias = 0.0f;
- rasterDesc.DepthBias = 0;
- }
-
- ID3D11RasterizerState *dx11RasterizerState = NULL;
- HRESULT result = mDevice->CreateRasterizerState(&rasterDesc, &dx11RasterizerState);
- if (FAILED(result) || !dx11RasterizerState)
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Unable to create a ID3D11RasterizerState, HRESULT: 0x%X.", result);
- }
-
- mRasterizerStateCache.insert(std::make_pair(key, std::make_pair(dx11RasterizerState, mCounter++)));
-
- *outRasterizerState = dx11RasterizerState;
- return gl::Error(GL_NO_ERROR);
- }
-}
-
-std::size_t RenderStateCache::hashDepthStencilState(const gl::DepthStencilState &dsState)
-{
- static const unsigned int seed = 0xABCDEF98;
-
- std::size_t hash = 0;
- MurmurHash3_x86_32(&dsState, sizeof(gl::DepthStencilState), seed, &hash);
- return hash;
-}
-
-bool RenderStateCache::compareDepthStencilStates(const gl::DepthStencilState &a, const gl::DepthStencilState &b)
-{
- return memcmp(&a, &b, sizeof(gl::DepthStencilState)) == 0;
-}
-
-gl::Error RenderStateCache::getDepthStencilState(const gl::DepthStencilState &originalState,
- bool disableDepth,
- bool disableStencil,
- ID3D11DepthStencilState **outDSState)
-{
- if (!mDevice)
+ // Disable culling if drawing points
+ if (rasterState.pointDrawMode)
{
- return gl::Error(GL_OUT_OF_MEMORY, "Internal error, RenderStateCache is not initialized.");
+ cullMode = D3D11_CULL_NONE;
}
- gl::DepthStencilState glState = originalState;
- if (disableDepth)
+ D3D11_RASTERIZER_DESC rasterDesc;
+ rasterDesc.FillMode = D3D11_FILL_SOLID;
+ rasterDesc.CullMode = cullMode;
+ rasterDesc.FrontCounterClockwise = (rasterState.frontFace == GL_CCW) ? FALSE : TRUE;
+ rasterDesc.DepthBiasClamp = 0.0f; // MSDN documentation of DepthBiasClamp implies a value of
+ // zero will preform no clamping, must be tested though.
+ rasterDesc.DepthClipEnable = TRUE;
+ rasterDesc.ScissorEnable = scissorEnabled ? TRUE : FALSE;
+ rasterDesc.MultisampleEnable = rasterState.multiSample;
+ rasterDesc.AntialiasedLineEnable = FALSE;
+
+ if (rasterState.polygonOffsetFill)
{
- glState.depthTest = false;
- glState.depthMask = false;
+ rasterDesc.SlopeScaledDepthBias = rasterState.polygonOffsetFactor;
+ rasterDesc.DepthBias = (INT)rasterState.polygonOffsetUnits;
}
-
- if (disableStencil)
+ else
{
- glState.stencilWritemask = 0;
- glState.stencilBackWritemask = 0;
- glState.stencilTest = false;
+ rasterDesc.SlopeScaledDepthBias = 0.0f;
+ rasterDesc.DepthBias = 0;
}
- auto keyIter = mDepthStencilStateCache.find(glState);
+ d3d11::RasterizerState dx11RasterizerState;
+ ANGLE_TRY(renderer->allocateResource(rasterDesc, &dx11RasterizerState));
+ *outRasterizerState = dx11RasterizerState.get();
+ mRasterizerStateCache.Put(key, std::move(dx11RasterizerState));
+
+ return gl::NoError();
+}
+
+gl::Error RenderStateCache::getDepthStencilState(Renderer11 *renderer,
+ const gl::DepthStencilState &glState,
+ const d3d11::DepthStencilState **outDSState)
+{
+ auto keyIter = mDepthStencilStateCache.Get(glState);
if (keyIter != mDepthStencilStateCache.end())
{
- DepthStencilStateCounterPair &state = keyIter->second;
- state.second = mCounter++;
- *outDSState = state.first;
- return gl::Error(GL_NO_ERROR);
+ *outDSState = &keyIter->second;
+ return gl::NoError();
}
- if (mDepthStencilStateCache.size() >= kMaxDepthStencilStates)
- {
- TRACE(
- "Overflowed the limit of %u depth stencil states, removing the least recently used "
- "to make room.",
- kMaxDepthStencilStates);
-
- auto leastRecentlyUsed = mDepthStencilStateCache.begin();
- for (auto i = mDepthStencilStateCache.begin(); i != mDepthStencilStateCache.end(); i++)
- {
- if (i->second.second < leastRecentlyUsed->second.second)
- {
- leastRecentlyUsed = i;
- }
- }
- SafeRelease(leastRecentlyUsed->second.first);
- mDepthStencilStateCache.erase(leastRecentlyUsed);
- }
+ TrimCache(kMaxStates, kGCLimit, "depth stencil state", &mDepthStencilStateCache);
D3D11_DEPTH_STENCIL_DESC dsDesc = {0};
dsDesc.DepthEnable = glState.depthTest ? TRUE : FALSE;
@@ -366,107 +208,66 @@ gl::Error RenderStateCache::getDepthStencilState(const gl::DepthStencilState &or
dsDesc.BackFace.StencilPassOp = ConvertStencilOp(glState.stencilBackPassDepthPass);
dsDesc.BackFace.StencilFunc = ConvertComparison(glState.stencilBackFunc);
- ID3D11DepthStencilState *dx11DepthStencilState = NULL;
- HRESULT result = mDevice->CreateDepthStencilState(&dsDesc, &dx11DepthStencilState);
- if (FAILED(result) || !dx11DepthStencilState)
- {
- return gl::Error(GL_OUT_OF_MEMORY,
- "Unable to create a ID3D11DepthStencilState, HRESULT: 0x%X.", result);
- }
+ d3d11::DepthStencilState dx11DepthStencilState;
+ ANGLE_TRY(renderer->allocateResource(dsDesc, &dx11DepthStencilState));
+ const auto &iter = mDepthStencilStateCache.Put(glState, std::move(dx11DepthStencilState));
- mDepthStencilStateCache.insert(
- std::make_pair(glState, std::make_pair(dx11DepthStencilState, mCounter++)));
+ *outDSState = &iter->second;
- *outDSState = dx11DepthStencilState;
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-std::size_t RenderStateCache::hashSamplerState(const gl::SamplerState &samplerState)
+gl::Error RenderStateCache::getSamplerState(Renderer11 *renderer,
+ const gl::SamplerState &samplerState,
+ ID3D11SamplerState **outSamplerState)
{
- static const unsigned int seed = 0xABCDEF98;
-
- std::size_t hash = 0;
- MurmurHash3_x86_32(&samplerState, sizeof(gl::SamplerState), seed, &hash);
- return hash;
-}
-
-bool RenderStateCache::compareSamplerStates(const gl::SamplerState &a, const gl::SamplerState &b)
-{
- return memcmp(&a, &b, sizeof(gl::SamplerState)) == 0;
-}
-
-gl::Error RenderStateCache::getSamplerState(const gl::SamplerState &samplerState, ID3D11SamplerState **outSamplerState)
-{
- if (!mDevice)
+ auto keyIter = mSamplerStateCache.Get(samplerState);
+ if (keyIter != mSamplerStateCache.end())
{
- return gl::Error(GL_OUT_OF_MEMORY, "Internal error, RenderStateCache is not initialized.");
+ *outSamplerState = keyIter->second.get();
+ return gl::NoError();
}
- SamplerStateMap::iterator keyIter = mSamplerStateCache.find(samplerState);
- if (keyIter != mSamplerStateCache.end())
+ TrimCache(kMaxStates, kGCLimit, "sampler state", &mSamplerStateCache);
+
+ const auto &featureLevel = renderer->getRenderer11DeviceCaps().featureLevel;
+
+ D3D11_SAMPLER_DESC samplerDesc;
+ samplerDesc.Filter =
+ gl_d3d11::ConvertFilter(samplerState.minFilter, samplerState.magFilter,
+ samplerState.maxAnisotropy, samplerState.compareMode);
+ samplerDesc.AddressU = gl_d3d11::ConvertTextureWrap(samplerState.wrapS);
+ samplerDesc.AddressV = gl_d3d11::ConvertTextureWrap(samplerState.wrapT);
+ samplerDesc.AddressW = gl_d3d11::ConvertTextureWrap(samplerState.wrapR);
+ samplerDesc.MipLODBias = 0;
+ samplerDesc.MaxAnisotropy =
+ gl_d3d11::ConvertMaxAnisotropy(samplerState.maxAnisotropy, featureLevel);
+ samplerDesc.ComparisonFunc = gl_d3d11::ConvertComparison(samplerState.compareFunc);
+ samplerDesc.BorderColor[0] = 0.0f;
+ samplerDesc.BorderColor[1] = 0.0f;
+ samplerDesc.BorderColor[2] = 0.0f;
+ samplerDesc.BorderColor[3] = 0.0f;
+ samplerDesc.MinLOD = samplerState.minLod;
+ samplerDesc.MaxLOD = samplerState.maxLod;
+
+ if (featureLevel <= D3D_FEATURE_LEVEL_9_3)
{
- SamplerStateCounterPair &state = keyIter->second;
- state.second = mCounter++;
- *outSamplerState = state.first;
- return gl::Error(GL_NO_ERROR);
+ // Check that maxLOD is nearly FLT_MAX (1000.0f is the default), since 9_3 doesn't support
+ // anything other than FLT_MAX. Note that Feature Level 9_* only supports GL ES 2.0, so the
+ // consumer of ANGLE can't modify the Max LOD themselves.
+ ASSERT(samplerState.maxLod >= 999.9f);
+
+ // Now just set MaxLOD to FLT_MAX. Other parts of the renderer (e.g. the non-zero max LOD
+ // workaround) should take account of this.
+ samplerDesc.MaxLOD = FLT_MAX;
}
- else
- {
- if (mSamplerStateCache.size() >= kMaxSamplerStates)
- {
- TRACE("Overflowed the limit of %u sampler states, removing the least recently used "
- "to make room.", kMaxSamplerStates);
-
- SamplerStateMap::iterator leastRecentlyUsed = mSamplerStateCache.begin();
- for (SamplerStateMap::iterator i = mSamplerStateCache.begin(); i != mSamplerStateCache.end(); i++)
- {
- if (i->second.second < leastRecentlyUsed->second.second)
- {
- leastRecentlyUsed = i;
- }
- }
- SafeRelease(leastRecentlyUsed->second.first);
- mSamplerStateCache.erase(leastRecentlyUsed);
- }
- D3D11_SAMPLER_DESC samplerDesc;
- samplerDesc.Filter = gl_d3d11::ConvertFilter(samplerState.minFilter, samplerState.magFilter,
- samplerState.maxAnisotropy, samplerState.compareMode);
- samplerDesc.AddressU = gl_d3d11::ConvertTextureWrap(samplerState.wrapS);
- samplerDesc.AddressV = gl_d3d11::ConvertTextureWrap(samplerState.wrapT);
- samplerDesc.AddressW = gl_d3d11::ConvertTextureWrap(samplerState.wrapR);
- samplerDesc.MipLODBias = 0;
- samplerDesc.MaxAnisotropy = static_cast<UINT>(samplerState.maxAnisotropy);
- samplerDesc.ComparisonFunc = gl_d3d11::ConvertComparison(samplerState.compareFunc);
- samplerDesc.BorderColor[0] = 0.0f;
- samplerDesc.BorderColor[1] = 0.0f;
- samplerDesc.BorderColor[2] = 0.0f;
- samplerDesc.BorderColor[3] = 0.0f;
- samplerDesc.MinLOD = samplerState.minLod;
- samplerDesc.MaxLOD = samplerState.maxLod;
-
- if (mRenderer->getRenderer11DeviceCaps().featureLevel <= D3D_FEATURE_LEVEL_9_3)
- {
- // Check that maxLOD is nearly FLT_MAX (1000.0f is the default), since 9_3 doesn't support anything other than FLT_MAX.
- // Note that Feature Level 9_* only supports GL ES 2.0, so the consumer of ANGLE can't modify the Max LOD themselves.
- ASSERT(samplerState.maxLod >= 999.9f);
-
- // Now just set MaxLOD to FLT_MAX. Other parts of the renderer (e.g. the non-zero max LOD workaround) should take account of this.
- samplerDesc.MaxLOD = FLT_MAX;
- }
+ d3d11::SamplerState dx11SamplerState;
+ ANGLE_TRY(renderer->allocateResource(samplerDesc, &dx11SamplerState));
+ *outSamplerState = dx11SamplerState.get();
+ mSamplerStateCache.Put(samplerState, std::move(dx11SamplerState));
- ID3D11SamplerState *dx11SamplerState = NULL;
- HRESULT result = mDevice->CreateSamplerState(&samplerDesc, &dx11SamplerState);
- if (FAILED(result) || !dx11SamplerState)
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Unable to create a ID3D11SamplerState, HRESULT: 0x%X.", result);
- }
-
- mSamplerStateCache.insert(std::make_pair(samplerState, std::make_pair(dx11SamplerState, mCounter++)));
-
- *outSamplerState = dx11SamplerState;
- return gl::Error(GL_NO_ERROR);
- }
+ return gl::NoError();
}
-}
+} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/RenderStateCache.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/RenderStateCache.h
index 82cb13903c..7501e83fc4 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/RenderStateCache.h
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/RenderStateCache.h
@@ -10,9 +10,11 @@
#ifndef LIBANGLE_RENDERER_D3D_D3D11_RENDERSTATECACHE_H_
#define LIBANGLE_RENDERER_D3D_D3D11_RENDERSTATECACHE_H_
-#include "libANGLE/angletypes.h"
-#include "libANGLE/Error.h"
#include "common/angleutils.h"
+#include "libANGLE/Error.h"
+#include "libANGLE/SizedMRUCache.h"
+#include "libANGLE/angletypes.h"
+#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
#include <unordered_map>
@@ -21,6 +23,42 @@ namespace gl
class Framebuffer;
}
+namespace std
+{
+template <>
+struct hash<rx::d3d11::BlendStateKey>
+{
+ size_t operator()(const rx::d3d11::BlendStateKey &key) const
+ {
+ return angle::ComputeGenericHash(key);
+ }
+};
+
+template <>
+struct hash<rx::d3d11::RasterizerStateKey>
+{
+ size_t operator()(const rx::d3d11::RasterizerStateKey &key) const
+ {
+ return angle::ComputeGenericHash(key);
+ }
+};
+
+template <>
+struct hash<gl::DepthStencilState>
+{
+ size_t operator()(const gl::DepthStencilState &key) const
+ {
+ return angle::ComputeGenericHash(key);
+ }
+};
+
+template <>
+struct hash<gl::SamplerState>
+{
+ size_t operator()(const gl::SamplerState &key) const { return angle::ComputeGenericHash(key); }
+};
+} // namespace std
+
namespace rx
{
class Renderer11;
@@ -28,87 +66,58 @@ class Renderer11;
class RenderStateCache : angle::NonCopyable
{
public:
- RenderStateCache(Renderer11 *renderer);
+ RenderStateCache();
virtual ~RenderStateCache();
- void initialize(ID3D11Device *device);
void clear();
- gl::Error getBlendState(const gl::Framebuffer *framebuffer, const gl::BlendState &blendState, ID3D11BlendState **outBlendState);
- gl::Error getRasterizerState(const gl::RasterizerState &rasterState, bool scissorEnabled, ID3D11RasterizerState **outRasterizerState);
- gl::Error getDepthStencilState(const gl::DepthStencilState &dsState,
- bool disableDepth,
- bool disableStencil,
- ID3D11DepthStencilState **outDSState);
- gl::Error getSamplerState(const gl::SamplerState &samplerState, ID3D11SamplerState **outSamplerState);
+ static d3d11::BlendStateKey GetBlendStateKey(const gl::Context *context,
+ const gl::Framebuffer *framebuffer,
+ const gl::BlendState &blendState);
+ gl::Error getBlendState(Renderer11 *renderer,
+ const d3d11::BlendStateKey &key,
+ const d3d11::BlendState **outBlendState);
+ gl::Error getRasterizerState(Renderer11 *renderer,
+ const gl::RasterizerState &rasterState,
+ bool scissorEnabled,
+ ID3D11RasterizerState **outRasterizerState);
+ gl::Error getDepthStencilState(Renderer11 *renderer,
+ const gl::DepthStencilState &dsState,
+ const d3d11::DepthStencilState **outDSState);
+ gl::Error getSamplerState(Renderer11 *renderer,
+ const gl::SamplerState &samplerState,
+ ID3D11SamplerState **outSamplerState);
private:
- Renderer11 *mRenderer;
- unsigned long long mCounter;
+ // MSDN's documentation of ID3D11Device::CreateBlendState, ID3D11Device::CreateRasterizerState,
+ // ID3D11Device::CreateDepthStencilState and ID3D11Device::CreateSamplerState claims the maximum
+ // number of unique states of each type an application can create is 4096
+ // TODO(ShahmeerEsmail): Revisit the cache sizes to make sure they are appropriate for most
+ // scenarios.
+ static constexpr unsigned int kMaxStates = 4096;
+
+ // The cache tries to clean up this many states at once.
+ static constexpr unsigned int kGCLimit = 128;
// Blend state cache
- struct BlendStateKey
- {
- gl::BlendState blendState;
- bool rtChannels[D3D11_SIMULTANEOUS_RENDER_TARGET_COUNT][4];
- };
- static std::size_t hashBlendState(const BlendStateKey &blendState);
- static bool compareBlendStates(const BlendStateKey &a, const BlendStateKey &b);
- static const unsigned int kMaxBlendStates;
-
- typedef std::size_t (*BlendStateHashFunction)(const BlendStateKey &);
- typedef bool (*BlendStateEqualityFunction)(const BlendStateKey &, const BlendStateKey &);
- typedef std::pair<ID3D11BlendState*, unsigned long long> BlendStateCounterPair;
- typedef std::unordered_map<BlendStateKey, BlendStateCounterPair, BlendStateHashFunction, BlendStateEqualityFunction> BlendStateMap;
+ using BlendStateMap = angle::base::HashingMRUCache<d3d11::BlendStateKey, d3d11::BlendState>;
BlendStateMap mBlendStateCache;
// Rasterizer state cache
- struct RasterizerStateKey
- {
- gl::RasterizerState rasterizerState;
- bool scissorEnabled;
- };
- static std::size_t hashRasterizerState(const RasterizerStateKey &rasterState);
- static bool compareRasterizerStates(const RasterizerStateKey &a, const RasterizerStateKey &b);
- static const unsigned int kMaxRasterizerStates;
-
- typedef std::size_t (*RasterizerStateHashFunction)(const RasterizerStateKey &);
- typedef bool (*RasterizerStateEqualityFunction)(const RasterizerStateKey &, const RasterizerStateKey &);
- typedef std::pair<ID3D11RasterizerState*, unsigned long long> RasterizerStateCounterPair;
- typedef std::unordered_map<RasterizerStateKey, RasterizerStateCounterPair, RasterizerStateHashFunction, RasterizerStateEqualityFunction> RasterizerStateMap;
+ using RasterizerStateMap =
+ angle::base::HashingMRUCache<d3d11::RasterizerStateKey, d3d11::RasterizerState>;
RasterizerStateMap mRasterizerStateCache;
// Depth stencil state cache
- static std::size_t hashDepthStencilState(const gl::DepthStencilState &dsState);
- static bool compareDepthStencilStates(const gl::DepthStencilState &a, const gl::DepthStencilState &b);
- static const unsigned int kMaxDepthStencilStates;
-
- typedef std::size_t (*DepthStencilStateHashFunction)(const gl::DepthStencilState &);
- typedef bool (*DepthStencilStateEqualityFunction)(const gl::DepthStencilState &, const gl::DepthStencilState &);
- typedef std::pair<ID3D11DepthStencilState*, unsigned long long> DepthStencilStateCounterPair;
- typedef std::unordered_map<gl::DepthStencilState,
- DepthStencilStateCounterPair,
- DepthStencilStateHashFunction,
- DepthStencilStateEqualityFunction> DepthStencilStateMap;
+ using DepthStencilStateMap =
+ angle::base::HashingMRUCache<gl::DepthStencilState, d3d11::DepthStencilState>;
DepthStencilStateMap mDepthStencilStateCache;
// Sample state cache
- static std::size_t hashSamplerState(const gl::SamplerState &samplerState);
- static bool compareSamplerStates(const gl::SamplerState &a, const gl::SamplerState &b);
- static const unsigned int kMaxSamplerStates;
-
- typedef std::size_t (*SamplerStateHashFunction)(const gl::SamplerState &);
- typedef bool (*SamplerStateEqualityFunction)(const gl::SamplerState &, const gl::SamplerState &);
- typedef std::pair<ID3D11SamplerState*, unsigned long long> SamplerStateCounterPair;
- typedef std::unordered_map<gl::SamplerState,
- SamplerStateCounterPair,
- SamplerStateHashFunction,
- SamplerStateEqualityFunction> SamplerStateMap;
+ using SamplerStateMap = angle::base::HashingMRUCache<gl::SamplerState, d3d11::SamplerState>;
SamplerStateMap mSamplerStateCache;
-
- ID3D11Device *mDevice;
};
-}
+} // namespace rx
#endif // LIBANGLE_RENDERER_D3D_D3D11_RENDERSTATECACHE_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/RenderTarget11.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/RenderTarget11.cpp
index cdfcacc287..594a382a72 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/RenderTarget11.cpp
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/RenderTarget11.cpp
@@ -18,7 +18,9 @@
namespace rx
{
-static bool getTextureProperties(ID3D11Resource *resource, unsigned int *mipLevels, unsigned int *samples)
+namespace
+{
+bool GetTextureProperties(ID3D11Resource *resource, unsigned int *mipLevels, unsigned int *samples)
{
ID3D11Texture1D *texture1D = d3d11::DynamicCastComObject<ID3D11Texture1D>(resource);
if (texture1D)
@@ -62,7 +64,7 @@ static bool getTextureProperties(ID3D11Resource *resource, unsigned int *mipLeve
return false;
}
-static unsigned int getRTVSubresourceIndex(ID3D11Resource *resource, ID3D11RenderTargetView *view)
+unsigned int GetRTVSubresourceIndex(ID3D11Resource *resource, ID3D11RenderTargetView *view)
{
D3D11_RENDER_TARGET_VIEW_DESC rtvDesc;
view->GetDesc(&rtvDesc);
@@ -72,58 +74,58 @@ static unsigned int getRTVSubresourceIndex(ID3D11Resource *resource, ID3D11Rende
switch (rtvDesc.ViewDimension)
{
- case D3D11_RTV_DIMENSION_TEXTURE1D:
- mipSlice = rtvDesc.Texture1D.MipSlice;
- arraySlice = 0;
- break;
-
- case D3D11_RTV_DIMENSION_TEXTURE1DARRAY:
- mipSlice = rtvDesc.Texture1DArray.MipSlice;
- arraySlice = rtvDesc.Texture1DArray.FirstArraySlice;
- break;
-
- case D3D11_RTV_DIMENSION_TEXTURE2D:
- mipSlice = rtvDesc.Texture2D.MipSlice;
- arraySlice = 0;
- break;
-
- case D3D11_RTV_DIMENSION_TEXTURE2DARRAY:
- mipSlice = rtvDesc.Texture2DArray.MipSlice;
- arraySlice = rtvDesc.Texture2DArray.FirstArraySlice;
- break;
-
- case D3D11_RTV_DIMENSION_TEXTURE2DMS:
- mipSlice = 0;
- arraySlice = 0;
- break;
-
- case D3D11_RTV_DIMENSION_TEXTURE2DMSARRAY:
- mipSlice = 0;
- arraySlice = rtvDesc.Texture2DMSArray.FirstArraySlice;
- break;
-
- case D3D11_RTV_DIMENSION_TEXTURE3D:
- mipSlice = rtvDesc.Texture3D.MipSlice;
- arraySlice = 0;
- break;
-
- case D3D11_RTV_DIMENSION_UNKNOWN:
- case D3D11_RTV_DIMENSION_BUFFER:
- UNIMPLEMENTED();
- break;
-
- default:
- UNREACHABLE();
- break;
+ case D3D11_RTV_DIMENSION_TEXTURE1D:
+ mipSlice = rtvDesc.Texture1D.MipSlice;
+ arraySlice = 0;
+ break;
+
+ case D3D11_RTV_DIMENSION_TEXTURE1DARRAY:
+ mipSlice = rtvDesc.Texture1DArray.MipSlice;
+ arraySlice = rtvDesc.Texture1DArray.FirstArraySlice;
+ break;
+
+ case D3D11_RTV_DIMENSION_TEXTURE2D:
+ mipSlice = rtvDesc.Texture2D.MipSlice;
+ arraySlice = 0;
+ break;
+
+ case D3D11_RTV_DIMENSION_TEXTURE2DARRAY:
+ mipSlice = rtvDesc.Texture2DArray.MipSlice;
+ arraySlice = rtvDesc.Texture2DArray.FirstArraySlice;
+ break;
+
+ case D3D11_RTV_DIMENSION_TEXTURE2DMS:
+ mipSlice = 0;
+ arraySlice = 0;
+ break;
+
+ case D3D11_RTV_DIMENSION_TEXTURE2DMSARRAY:
+ mipSlice = 0;
+ arraySlice = rtvDesc.Texture2DMSArray.FirstArraySlice;
+ break;
+
+ case D3D11_RTV_DIMENSION_TEXTURE3D:
+ mipSlice = rtvDesc.Texture3D.MipSlice;
+ arraySlice = 0;
+ break;
+
+ case D3D11_RTV_DIMENSION_UNKNOWN:
+ case D3D11_RTV_DIMENSION_BUFFER:
+ UNIMPLEMENTED();
+ break;
+
+ default:
+ UNREACHABLE();
+ break;
}
unsigned int mipLevels, samples;
- getTextureProperties(resource, &mipLevels, &samples);
+ GetTextureProperties(resource, &mipLevels, &samples);
return D3D11CalcSubresource(mipSlice, arraySlice, mipLevels);
}
-static unsigned int getDSVSubresourceIndex(ID3D11Resource *resource, ID3D11DepthStencilView *view)
+unsigned int GetDSVSubresourceIndex(ID3D11Resource *resource, ID3D11DepthStencilView *view)
{
D3D11_DEPTH_STENCIL_VIEW_DESC dsvDesc;
view->GetDesc(&dsvDesc);
@@ -133,157 +135,170 @@ static unsigned int getDSVSubresourceIndex(ID3D11Resource *resource, ID3D11Depth
switch (dsvDesc.ViewDimension)
{
- case D3D11_DSV_DIMENSION_TEXTURE1D:
- mipSlice = dsvDesc.Texture1D.MipSlice;
- arraySlice = 0;
- break;
-
- case D3D11_DSV_DIMENSION_TEXTURE1DARRAY:
- mipSlice = dsvDesc.Texture1DArray.MipSlice;
- arraySlice = dsvDesc.Texture1DArray.FirstArraySlice;
- break;
-
- case D3D11_DSV_DIMENSION_TEXTURE2D:
- mipSlice = dsvDesc.Texture2D.MipSlice;
- arraySlice = 0;
- break;
-
- case D3D11_DSV_DIMENSION_TEXTURE2DARRAY:
- mipSlice = dsvDesc.Texture2DArray.MipSlice;
- arraySlice = dsvDesc.Texture2DArray.FirstArraySlice;
- break;
-
- case D3D11_DSV_DIMENSION_TEXTURE2DMS:
- mipSlice = 0;
- arraySlice = 0;
- break;
-
- case D3D11_DSV_DIMENSION_TEXTURE2DMSARRAY:
- mipSlice = 0;
- arraySlice = dsvDesc.Texture2DMSArray.FirstArraySlice;
- break;
-
- case D3D11_DSV_DIMENSION_UNKNOWN:
- UNIMPLEMENTED();
- break;
-
- default:
- UNREACHABLE();
- break;
+ case D3D11_DSV_DIMENSION_TEXTURE1D:
+ mipSlice = dsvDesc.Texture1D.MipSlice;
+ arraySlice = 0;
+ break;
+
+ case D3D11_DSV_DIMENSION_TEXTURE1DARRAY:
+ mipSlice = dsvDesc.Texture1DArray.MipSlice;
+ arraySlice = dsvDesc.Texture1DArray.FirstArraySlice;
+ break;
+
+ case D3D11_DSV_DIMENSION_TEXTURE2D:
+ mipSlice = dsvDesc.Texture2D.MipSlice;
+ arraySlice = 0;
+ break;
+
+ case D3D11_DSV_DIMENSION_TEXTURE2DARRAY:
+ mipSlice = dsvDesc.Texture2DArray.MipSlice;
+ arraySlice = dsvDesc.Texture2DArray.FirstArraySlice;
+ break;
+
+ case D3D11_DSV_DIMENSION_TEXTURE2DMS:
+ mipSlice = 0;
+ arraySlice = 0;
+ break;
+
+ case D3D11_DSV_DIMENSION_TEXTURE2DMSARRAY:
+ mipSlice = 0;
+ arraySlice = dsvDesc.Texture2DMSArray.FirstArraySlice;
+ break;
+
+ case D3D11_DSV_DIMENSION_UNKNOWN:
+ UNIMPLEMENTED();
+ break;
+
+ default:
+ UNREACHABLE();
+ break;
}
unsigned int mipLevels, samples;
- getTextureProperties(resource, &mipLevels, &samples);
+ GetTextureProperties(resource, &mipLevels, &samples);
return D3D11CalcSubresource(mipSlice, arraySlice, mipLevels);
}
-TextureRenderTarget11::TextureRenderTarget11(ID3D11RenderTargetView *rtv, ID3D11Resource *resource, ID3D11ShaderResourceView *srv,
- GLenum internalFormat, GLsizei width, GLsizei height, GLsizei depth, GLsizei samples)
- : mWidth(width),
+GLenum GetSurfaceRTFormat(bool depth, SwapChain11 *swapChain)
+{
+ return (depth ? swapChain->getDepthBufferInternalFormat()
+ : swapChain->getRenderTargetInternalFormat());
+}
+
+const d3d11::Format &GetSurfaceFormatSet(bool depth, SwapChain11 *swapChain, Renderer11 *renderer)
+{
+ return d3d11::Format::Get(GetSurfaceRTFormat(depth, swapChain),
+ renderer->getRenderer11DeviceCaps());
+}
+
+} // anonymous namespace
+
+RenderTarget11::RenderTarget11(const d3d11::Format &formatSet) : mFormatSet(formatSet)
+{
+}
+
+RenderTarget11::~RenderTarget11()
+{
+ ASSERT(mBroadcastChannel.empty());
+}
+
+void RenderTarget11::signalDirty(const gl::Context *context)
+{
+ mBroadcastChannel.signal(context);
+
+ // Clear the list. We can't do this in the receiver because it would mutate during iteration.
+ mBroadcastChannel.reset();
+}
+
+TextureRenderTarget11::TextureRenderTarget11(d3d11::RenderTargetView &&rtv,
+ const TextureHelper11 &resource,
+ const d3d11::SharedSRV &srv,
+ const d3d11::SharedSRV &blitSRV,
+ GLenum internalFormat,
+ const d3d11::Format &formatSet,
+ GLsizei width,
+ GLsizei height,
+ GLsizei depth,
+ GLsizei samples)
+ : RenderTarget11(formatSet),
+ mWidth(width),
mHeight(height),
mDepth(depth),
mInternalFormat(internalFormat),
- mDXGIFormat(DXGI_FORMAT_UNKNOWN),
mSamples(samples),
mSubresourceIndex(0),
mTexture(resource),
- mRenderTarget(rtv),
- mDepthStencil(NULL),
- mShaderResource(srv)
+ mRenderTarget(std::move(rtv)),
+ mDepthStencil(),
+ mShaderResource(srv.makeCopy()),
+ mBlitShaderResource(blitSRV.makeCopy())
{
- if (mTexture)
- {
- mTexture->AddRef();
- }
-
- if (mRenderTarget)
- {
- mRenderTarget->AddRef();
- }
-
- if (mShaderResource)
- {
- mShaderResource->AddRef();
- }
-
- if (mRenderTarget && mTexture)
+ if (mRenderTarget.valid() && mTexture.valid())
{
- mSubresourceIndex = getRTVSubresourceIndex(mTexture, mRenderTarget);
-
- D3D11_RENDER_TARGET_VIEW_DESC desc;
- mRenderTarget->GetDesc(&desc);
- mDXGIFormat = desc.Format;
+ mSubresourceIndex = GetRTVSubresourceIndex(mTexture.get(), mRenderTarget.get());
}
+ ASSERT(mFormatSet.formatID != angle::Format::ID::NONE || mWidth == 0 || mHeight == 0);
}
-TextureRenderTarget11::TextureRenderTarget11(ID3D11DepthStencilView *dsv, ID3D11Resource *resource, ID3D11ShaderResourceView *srv,
- GLenum internalFormat, GLsizei width, GLsizei height, GLsizei depth, GLsizei samples)
- : mWidth(width),
+TextureRenderTarget11::TextureRenderTarget11(d3d11::DepthStencilView &&dsv,
+ const TextureHelper11 &resource,
+ const d3d11::SharedSRV &srv,
+ GLenum internalFormat,
+ const d3d11::Format &formatSet,
+ GLsizei width,
+ GLsizei height,
+ GLsizei depth,
+ GLsizei samples)
+ : RenderTarget11(formatSet),
+ mWidth(width),
mHeight(height),
mDepth(depth),
mInternalFormat(internalFormat),
- mDXGIFormat(DXGI_FORMAT_UNKNOWN),
mSamples(samples),
mSubresourceIndex(0),
mTexture(resource),
- mRenderTarget(NULL),
- mDepthStencil(dsv),
- mShaderResource(srv)
+ mRenderTarget(),
+ mDepthStencil(std::move(dsv)),
+ mShaderResource(srv.makeCopy()),
+ mBlitShaderResource()
{
- if (mTexture)
+ if (mDepthStencil.valid() && mTexture.valid())
{
- mTexture->AddRef();
- }
-
- if (mDepthStencil)
- {
- mDepthStencil->AddRef();
- }
-
- if (mShaderResource)
- {
- mShaderResource->AddRef();
- }
-
- if (mDepthStencil && mTexture)
- {
- mSubresourceIndex = getDSVSubresourceIndex(mTexture, mDepthStencil);
-
- D3D11_DEPTH_STENCIL_VIEW_DESC desc;
- mDepthStencil->GetDesc(&desc);
- mDXGIFormat = desc.Format;
+ mSubresourceIndex = GetDSVSubresourceIndex(mTexture.get(), mDepthStencil.get());
}
+ ASSERT(mFormatSet.formatID != angle::Format::ID::NONE || mWidth == 0 || mHeight == 0);
}
TextureRenderTarget11::~TextureRenderTarget11()
{
- SafeRelease(mTexture);
- SafeRelease(mRenderTarget);
- SafeRelease(mDepthStencil);
- SafeRelease(mShaderResource);
}
-ID3D11Resource *TextureRenderTarget11::getTexture() const
+const TextureHelper11 &TextureRenderTarget11::getTexture() const
{
return mTexture;
}
-ID3D11RenderTargetView *TextureRenderTarget11::getRenderTargetView() const
+const d3d11::RenderTargetView &TextureRenderTarget11::getRenderTargetView() const
{
return mRenderTarget;
}
-ID3D11DepthStencilView *TextureRenderTarget11::getDepthStencilView() const
+const d3d11::DepthStencilView &TextureRenderTarget11::getDepthStencilView() const
{
return mDepthStencil;
}
-ID3D11ShaderResourceView *TextureRenderTarget11::getShaderResourceView() const
+const d3d11::SharedSRV &TextureRenderTarget11::getShaderResourceView() const
{
return mShaderResource;
}
+const d3d11::SharedSRV &TextureRenderTarget11::getBlitShaderResourceView() const
+{
+ return mBlitShaderResource;
+}
+
GLsizei TextureRenderTarget11::getWidth() const
{
return mWidth;
@@ -314,14 +329,11 @@ unsigned int TextureRenderTarget11::getSubresourceIndex() const
return mSubresourceIndex;
}
-DXGI_FORMAT TextureRenderTarget11::getDXGIFormat() const
-{
- return mDXGIFormat;
-}
-
-SurfaceRenderTarget11::SurfaceRenderTarget11(SwapChain11 *swapChain, Renderer11 *renderer, bool depth)
- : mSwapChain(swapChain),
- mRenderer(renderer),
+SurfaceRenderTarget11::SurfaceRenderTarget11(SwapChain11 *swapChain,
+ Renderer11 *renderer,
+ bool depth)
+ : RenderTarget11(GetSurfaceFormatSet(depth, swapChain, renderer)),
+ mSwapChain(swapChain),
mDepth(depth)
{
ASSERT(mSwapChain);
@@ -348,43 +360,46 @@ GLsizei SurfaceRenderTarget11::getDepth() const
GLenum SurfaceRenderTarget11::getInternalFormat() const
{
- return (mDepth ? mSwapChain->GetDepthBufferInternalFormat() : mSwapChain->GetRenderTargetInternalFormat());
+ return GetSurfaceRTFormat(mDepth, mSwapChain);
}
GLsizei SurfaceRenderTarget11::getSamples() const
{
- // Our EGL surfaces do not support multisampling.
- return 0;
+ return mSwapChain->getSamples();
}
-ID3D11Resource *SurfaceRenderTarget11::getTexture() const
+const TextureHelper11 &SurfaceRenderTarget11::getTexture() const
{
return (mDepth ? mSwapChain->getDepthStencilTexture() : mSwapChain->getOffscreenTexture());
}
-ID3D11RenderTargetView *SurfaceRenderTarget11::getRenderTargetView() const
+const d3d11::RenderTargetView &SurfaceRenderTarget11::getRenderTargetView() const
{
- return (mDepth ? NULL : mSwapChain->getRenderTarget());
+ ASSERT(!mDepth);
+ return mSwapChain->getRenderTarget();
}
-ID3D11DepthStencilView *SurfaceRenderTarget11::getDepthStencilView() const
+const d3d11::DepthStencilView &SurfaceRenderTarget11::getDepthStencilView() const
{
- return (mDepth ? mSwapChain->getDepthStencil() : NULL);
+ ASSERT(mDepth);
+ return mSwapChain->getDepthStencil();
}
-ID3D11ShaderResourceView *SurfaceRenderTarget11::getShaderResourceView() const
+const d3d11::SharedSRV &SurfaceRenderTarget11::getShaderResourceView() const
{
- return (mDepth ? mSwapChain->getDepthStencilShaderResource() : mSwapChain->getRenderTargetShaderResource());
+ return (mDepth ? mSwapChain->getDepthStencilShaderResource()
+ : mSwapChain->getRenderTargetShaderResource());
}
-unsigned int SurfaceRenderTarget11::getSubresourceIndex() const
+const d3d11::SharedSRV &SurfaceRenderTarget11::getBlitShaderResourceView() const
{
- return 0;
+ // The SurfaceRenderTargetView format should always be such that the normal SRV works for blits.
+ return getShaderResourceView();
}
-DXGI_FORMAT SurfaceRenderTarget11::getDXGIFormat() const
+unsigned int SurfaceRenderTarget11::getSubresourceIndex() const
{
- return d3d11::GetTextureFormatInfo(getInternalFormat(), mRenderer->getRenderer11DeviceCaps()).texFormat;
+ return 0;
}
-}
+} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/RenderTarget11.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/RenderTarget11.h
index d47b237c09..db49cac9f5 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/RenderTarget11.h
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/RenderTarget11.h
@@ -11,6 +11,9 @@
#define LIBANGLE_RENDERER_D3D_D3D11_RENDERTARGET11_H_
#include "libANGLE/renderer/d3d/RenderTargetD3D.h"
+#include "libANGLE/renderer/d3d/d3d11/ResourceManager11.h"
+#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
+#include "libANGLE/renderer/d3d/d3d11/texture_format_table.h"
namespace rx
{
@@ -20,28 +23,51 @@ class Renderer11;
class RenderTarget11 : public RenderTargetD3D
{
public:
- RenderTarget11() { }
- virtual ~RenderTarget11() { }
+ RenderTarget11(const d3d11::Format &formatSet);
+ ~RenderTarget11() override;
- virtual ID3D11Resource *getTexture() const = 0;
- virtual ID3D11RenderTargetView *getRenderTargetView() const = 0;
- virtual ID3D11DepthStencilView *getDepthStencilView() const = 0;
- virtual ID3D11ShaderResourceView *getShaderResourceView() const = 0;
+ virtual const TextureHelper11 &getTexture() const = 0;
+ virtual const d3d11::RenderTargetView &getRenderTargetView() const = 0;
+ virtual const d3d11::DepthStencilView &getDepthStencilView() const = 0;
+ virtual const d3d11::SharedSRV &getShaderResourceView() const = 0;
+ virtual const d3d11::SharedSRV &getBlitShaderResourceView() const = 0;
virtual unsigned int getSubresourceIndex() const = 0;
- virtual DXGI_FORMAT getDXGIFormat() const = 0;
+ void signalDirty(const gl::Context *context) override;
+ OnRenderTargetDirtyChannel *getBroadcastChannel() { return &mBroadcastChannel; }
+
+ const d3d11::Format &getFormatSet() const { return mFormatSet; }
+
+ protected:
+ OnRenderTargetDirtyChannel mBroadcastChannel;
+ const d3d11::Format &mFormatSet;
};
class TextureRenderTarget11 : public RenderTarget11
{
public:
// TextureRenderTarget11 takes ownership of any D3D11 resources it is given and will AddRef them
- TextureRenderTarget11(ID3D11RenderTargetView *rtv, ID3D11Resource *resource, ID3D11ShaderResourceView *srv,
- GLenum internalFormat, GLsizei width, GLsizei height, GLsizei depth, GLsizei samples);
- TextureRenderTarget11(ID3D11DepthStencilView *dsv, ID3D11Resource *resource, ID3D11ShaderResourceView *srv,
- GLenum internalFormat, GLsizei width, GLsizei height, GLsizei depth, GLsizei samples);
- virtual ~TextureRenderTarget11();
+ TextureRenderTarget11(d3d11::RenderTargetView &&rtv,
+ const TextureHelper11 &resource,
+ const d3d11::SharedSRV &srv,
+ const d3d11::SharedSRV &blitSRV,
+ GLenum internalFormat,
+ const d3d11::Format &formatSet,
+ GLsizei width,
+ GLsizei height,
+ GLsizei depth,
+ GLsizei samples);
+ TextureRenderTarget11(d3d11::DepthStencilView &&dsv,
+ const TextureHelper11 &resource,
+ const d3d11::SharedSRV &srv,
+ GLenum internalFormat,
+ const d3d11::Format &formatSet,
+ GLsizei width,
+ GLsizei height,
+ GLsizei depth,
+ GLsizei samples);
+ ~TextureRenderTarget11() override;
GLsizei getWidth() const override;
GLsizei getHeight() const override;
@@ -49,35 +75,37 @@ class TextureRenderTarget11 : public RenderTarget11
GLenum getInternalFormat() const override;
GLsizei getSamples() const override;
- ID3D11Resource *getTexture() const override;
- ID3D11RenderTargetView *getRenderTargetView() const override;
- ID3D11DepthStencilView *getDepthStencilView() const override;
- ID3D11ShaderResourceView *getShaderResourceView() const override;
+ const TextureHelper11 &getTexture() const override;
+ const d3d11::RenderTargetView &getRenderTargetView() const override;
+ const d3d11::DepthStencilView &getDepthStencilView() const override;
+ const d3d11::SharedSRV &getShaderResourceView() const override;
+ const d3d11::SharedSRV &getBlitShaderResourceView() const override;
unsigned int getSubresourceIndex() const override;
- DXGI_FORMAT getDXGIFormat() const override;
-
private:
GLsizei mWidth;
GLsizei mHeight;
GLsizei mDepth;
GLenum mInternalFormat;
- DXGI_FORMAT mDXGIFormat;
GLsizei mSamples;
unsigned int mSubresourceIndex;
- ID3D11Resource *mTexture;
- ID3D11RenderTargetView *mRenderTarget;
- ID3D11DepthStencilView *mDepthStencil;
- ID3D11ShaderResourceView *mShaderResource;
+ TextureHelper11 mTexture;
+ d3d11::RenderTargetView mRenderTarget;
+ d3d11::DepthStencilView mDepthStencil;
+ d3d11::SharedSRV mShaderResource;
+
+ // Shader resource view to use with internal blit shaders. Not set for depth/stencil render
+ // targets.
+ d3d11::SharedSRV mBlitShaderResource;
};
class SurfaceRenderTarget11 : public RenderTarget11
{
public:
SurfaceRenderTarget11(SwapChain11 *swapChain, Renderer11 *renderer, bool depth);
- virtual ~SurfaceRenderTarget11();
+ ~SurfaceRenderTarget11() override;
GLsizei getWidth() const override;
GLsizei getHeight() const override;
@@ -85,21 +113,19 @@ class SurfaceRenderTarget11 : public RenderTarget11
GLenum getInternalFormat() const override;
GLsizei getSamples() const override;
- ID3D11Resource *getTexture() const override;
- ID3D11RenderTargetView *getRenderTargetView() const override;
- ID3D11DepthStencilView *getDepthStencilView() const override;
- ID3D11ShaderResourceView *getShaderResourceView() const override;
+ const TextureHelper11 &getTexture() const override;
+ const d3d11::RenderTargetView &getRenderTargetView() const override;
+ const d3d11::DepthStencilView &getDepthStencilView() const override;
+ const d3d11::SharedSRV &getShaderResourceView() const override;
+ const d3d11::SharedSRV &getBlitShaderResourceView() const override;
unsigned int getSubresourceIndex() const override;
- DXGI_FORMAT getDXGIFormat() const override;
-
private:
SwapChain11 *mSwapChain;
- Renderer11 *mRenderer;
bool mDepth;
};
-}
+} // namespace rx
#endif // LIBANGLE_RENDERER_D3D_D3D11_RENDERTARGET11_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Renderer11.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Renderer11.cpp
index 5118bdbe9c..b0ef9abddc 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Renderer11.cpp
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Renderer11.cpp
@@ -9,56 +9,64 @@
#include "libANGLE/renderer/d3d/d3d11/Renderer11.h"
#include <EGL/eglext.h>
+#include <versionhelpers.h>
#include <sstream>
-#if !defined(ANGLE_MINGW32_COMPAT) && WINAPI_FAMILY != WINAPI_FAMILY_PHONE_APP
-#include <VersionHelpers.h>
-#endif
#include "common/tls.h"
#include "common/utilities.h"
#include "libANGLE/Buffer.h"
+#include "libANGLE/Context.h"
#include "libANGLE/Display.h"
-#include "libANGLE/formatutils.h"
#include "libANGLE/Framebuffer.h"
#include "libANGLE/FramebufferAttachment.h"
-#include "libANGLE/histogram_macros.h"
#include "libANGLE/Program.h"
+#include "libANGLE/State.h"
+#include "libANGLE/Surface.h"
+#include "libANGLE/formatutils.h"
+#include "libANGLE/histogram_macros.h"
#include "libANGLE/renderer/d3d/CompilerD3D.h"
+#include "libANGLE/renderer/d3d/DeviceD3D.h"
+#include "libANGLE/renderer/d3d/DisplayD3D.h"
+#include "libANGLE/renderer/d3d/FramebufferD3D.h"
+#include "libANGLE/renderer/d3d/IndexDataManager.h"
+#include "libANGLE/renderer/d3d/ProgramD3D.h"
+#include "libANGLE/renderer/d3d/RenderbufferD3D.h"
+#include "libANGLE/renderer/d3d/ShaderD3D.h"
+#include "libANGLE/renderer/d3d/SurfaceD3D.h"
+#include "libANGLE/renderer/d3d/TextureD3D.h"
+#include "libANGLE/renderer/d3d/VertexDataManager.h"
#include "libANGLE/renderer/d3d/d3d11/Blit11.h"
#include "libANGLE/renderer/d3d/d3d11/Buffer11.h"
#include "libANGLE/renderer/d3d/d3d11/Clear11.h"
-#include "libANGLE/renderer/d3d/d3d11/dxgi_support_table.h"
+#include "libANGLE/renderer/d3d/d3d11/Context11.h"
#include "libANGLE/renderer/d3d/d3d11/Fence11.h"
-#include "libANGLE/renderer/d3d/d3d11/formatutils11.h"
#include "libANGLE/renderer/d3d/d3d11/Framebuffer11.h"
#include "libANGLE/renderer/d3d/d3d11/Image11.h"
#include "libANGLE/renderer/d3d/d3d11/IndexBuffer11.h"
#include "libANGLE/renderer/d3d/d3d11/PixelTransfer11.h"
#include "libANGLE/renderer/d3d/d3d11/Query11.h"
-#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
#include "libANGLE/renderer/d3d/d3d11/RenderTarget11.h"
#include "libANGLE/renderer/d3d/d3d11/ShaderExecutable11.h"
+#include "libANGLE/renderer/d3d/d3d11/StreamProducerNV12.h"
#include "libANGLE/renderer/d3d/d3d11/SwapChain11.h"
-#include "libANGLE/renderer/d3d/d3d11/texture_format_table.h"
#include "libANGLE/renderer/d3d/d3d11/TextureStorage11.h"
+#include "libANGLE/renderer/d3d/d3d11/TransformFeedback11.h"
#include "libANGLE/renderer/d3d/d3d11/Trim11.h"
#include "libANGLE/renderer/d3d/d3d11/VertexArray11.h"
#include "libANGLE/renderer/d3d/d3d11/VertexBuffer11.h"
-#include "libANGLE/renderer/d3d/CompilerD3D.h"
-#include "libANGLE/renderer/d3d/DeviceD3D.h"
-#include "libANGLE/renderer/d3d/FramebufferD3D.h"
-#include "libANGLE/renderer/d3d/IndexDataManager.h"
-#include "libANGLE/renderer/d3d/ProgramD3D.h"
-#include "libANGLE/renderer/d3d/RenderbufferD3D.h"
-#include "libANGLE/renderer/d3d/ShaderD3D.h"
-#include "libANGLE/renderer/d3d/SurfaceD3D.h"
-#include "libANGLE/renderer/d3d/TextureD3D.h"
-#include "libANGLE/renderer/d3d/TransformFeedbackD3D.h"
-#include "libANGLE/renderer/d3d/VertexDataManager.h"
-#include "libANGLE/State.h"
-#include "libANGLE/Surface.h"
+#include "libANGLE/renderer/d3d/d3d11/dxgi_support_table.h"
+#include "libANGLE/renderer/d3d/d3d11/formatutils11.h"
+#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
+#include "libANGLE/renderer/d3d/d3d11/texture_format_table.h"
+#include "libANGLE/renderer/renderer_utils.h"
#include "third_party/trace_event/trace_event.h"
+#ifdef ANGLE_ENABLE_WINDOWS_STORE
+#include "libANGLE/renderer/d3d/d3d11/winrt/NativeWindow11WinRT.h"
+#else
+#include "libANGLE/renderer/d3d/d3d11/win32/NativeWindow11Win32.h"
+#endif
+
// Include the D3D9 debug annotator header for use by the desktop D3D11 renderer
// because the D3D11 interface method ID3DUserDefinedAnnotation::GetStatus
// doesn't work with the Graphics Diagnostics tools in Visual Studio 2013.
@@ -72,12 +80,6 @@
#define ANGLE_SKIP_DXGI_1_2_CHECK 0
#endif
-#ifdef _DEBUG
-// this flag enables suppressing some spurious warnings that pop up in certain WebGL samples
-// and conformance tests. to enable all warnings, remove this define.
-#define ANGLE_SUPPRESS_D3D11_HAZARD_WARNINGS 1
-#endif
-
namespace rx
{
@@ -89,25 +91,6 @@ enum
MAX_TEXTURE_IMAGE_UNITS_VTF_SM4 = 16
};
-#if defined(ANGLE_ENABLE_D3D11_1)
-void CalculateConstantBufferParams(GLintptr offset, GLsizeiptr size, UINT *outFirstConstant, UINT *outNumConstants)
-{
- // The offset must be aligned to 256 bytes (should have been enforced by glBindBufferRange).
- ASSERT(offset % 256 == 0);
-
- // firstConstant and numConstants are expressed in constants of 16-bytes. Furthermore they must be a multiple of 16 constants.
- *outFirstConstant = static_cast<UINT>(offset / 16);
-
- // The GL size is not required to be aligned to a 256 bytes boundary.
- // Round the size up to a 256 bytes boundary then express the results in constants of 16-bytes.
- *outNumConstants = static_cast<UINT>(rx::roundUp(size, static_cast<GLsizeiptr>(256)) / 16);
-
- // Since the size is rounded up, firstConstant + numConstants may be bigger than the actual size of the buffer.
- // This behaviour is explictly allowed according to the documentation on ID3D11DeviceContext1::PSSetConstantBuffers1
- // https://msdn.microsoft.com/en-us/library/windows/desktop/hh404649%28v=vs.85%29.aspx
-}
-#endif
-
enum ANGLEFeatureLevel
{
ANGLE_FEATURE_LEVEL_INVALID,
@@ -123,14 +106,18 @@ ANGLEFeatureLevel GetANGLEFeatureLevel(D3D_FEATURE_LEVEL d3dFeatureLevel)
{
switch (d3dFeatureLevel)
{
- case D3D_FEATURE_LEVEL_9_3: return ANGLE_FEATURE_LEVEL_9_3;
- case D3D_FEATURE_LEVEL_10_0: return ANGLE_FEATURE_LEVEL_10_0;
- case D3D_FEATURE_LEVEL_10_1: return ANGLE_FEATURE_LEVEL_10_1;
- case D3D_FEATURE_LEVEL_11_0: return ANGLE_FEATURE_LEVEL_11_0;
- // Note: we don't ever request a 11_1 device, because this gives
- // an E_INVALIDARG error on systems that don't have the platform update.
- case D3D_FEATURE_LEVEL_11_1: return ANGLE_FEATURE_LEVEL_11_1;
- default: return ANGLE_FEATURE_LEVEL_INVALID;
+ case D3D_FEATURE_LEVEL_9_3:
+ return ANGLE_FEATURE_LEVEL_9_3;
+ case D3D_FEATURE_LEVEL_10_0:
+ return ANGLE_FEATURE_LEVEL_10_0;
+ case D3D_FEATURE_LEVEL_10_1:
+ return ANGLE_FEATURE_LEVEL_10_1;
+ case D3D_FEATURE_LEVEL_11_0:
+ return ANGLE_FEATURE_LEVEL_11_0;
+ case D3D_FEATURE_LEVEL_11_1:
+ return ANGLE_FEATURE_LEVEL_11_1;
+ default:
+ return ANGLE_FEATURE_LEVEL_INVALID;
}
}
@@ -144,7 +131,7 @@ void SetLineLoopIndices(GLuint *dest, size_t count)
}
template <typename T>
-void CopyLineLoopIndices(const GLvoid *indices, GLuint *dest, size_t count)
+void CopyLineLoopIndices(const void *indices, GLuint *dest, size_t count)
{
const T *srcPtr = static_cast<const T *>(indices);
for (size_t i = 0; i < count; ++i)
@@ -165,7 +152,7 @@ void SetTriangleFanIndices(GLuint *destPtr, size_t numTris)
}
template <typename T>
-void CopyLineLoopIndicesWithRestart(const GLvoid *indices,
+void CopyLineLoopIndicesWithRestart(const void *indices,
size_t count,
GLenum indexType,
std::vector<GLuint> *bufferOut)
@@ -206,7 +193,7 @@ void CopyLineLoopIndicesWithRestart(const GLvoid *indices,
}
}
-void GetLineLoopIndices(const GLvoid *indices,
+void GetLineLoopIndices(const void *indices,
GLenum indexType,
GLuint count,
bool usePrimitiveRestartFixedIndex,
@@ -257,7 +244,7 @@ void GetLineLoopIndices(const GLvoid *indices,
}
template <typename T>
-void CopyTriangleFanIndices(const GLvoid *indices, GLuint *destPtr, size_t numTris)
+void CopyTriangleFanIndices(const void *indices, GLuint *destPtr, size_t numTris)
{
const T *srcPtr = static_cast<const T *>(indices);
@@ -270,7 +257,7 @@ void CopyTriangleFanIndices(const GLvoid *indices, GLuint *destPtr, size_t numTr
}
template <typename T>
-void CopyTriangleFanIndicesWithRestart(const GLvoid *indices,
+void CopyTriangleFanIndicesWithRestart(const void *indices,
GLuint indexCount,
GLenum indexType,
std::vector<GLuint> *bufferOut)
@@ -314,7 +301,7 @@ void CopyTriangleFanIndicesWithRestart(const GLvoid *indices,
}
}
-void GetTriFanIndices(const GLvoid *indices,
+void GetTriFanIndices(const void *indices,
GLenum indexType,
GLuint count,
bool usePrimitiveRestartFixedIndex,
@@ -365,60 +352,135 @@ void GetTriFanIndices(const GLvoid *indices,
}
}
+bool DrawCallNeedsTranslation(const gl::Context *context, GLenum mode)
+{
+ const auto &glState = context->getGLState();
+ const gl::VertexArray *vertexArray = glState.getVertexArray();
+ VertexArray11 *vertexArray11 = GetImplAs<VertexArray11>(vertexArray);
+ // Direct drawing doesn't support dynamic attribute storage since it needs the first and count
+ // to translate when applyVertexBuffer. GL_LINE_LOOP and GL_TRIANGLE_FAN are not supported
+ // either since we need to simulate them in D3D.
+ if (vertexArray11->hasActiveDynamicAttrib(context) || mode == GL_LINE_LOOP ||
+ mode == GL_TRIANGLE_FAN)
+ {
+ return true;
+ }
+
+ ProgramD3D *programD3D = GetImplAs<ProgramD3D>(glState.getProgram());
+ if (InstancedPointSpritesActive(programD3D, mode))
+ {
+ return true;
+ }
+
+ return false;
+}
+
+bool IsArrayRTV(ID3D11RenderTargetView *rtv)
+{
+ D3D11_RENDER_TARGET_VIEW_DESC desc;
+ rtv->GetDesc(&desc);
+ if (desc.ViewDimension == D3D11_RTV_DIMENSION_TEXTURE1DARRAY &&
+ desc.Texture1DArray.ArraySize > 1)
+ return true;
+ if (desc.ViewDimension == D3D11_RTV_DIMENSION_TEXTURE2DARRAY &&
+ desc.Texture2DArray.ArraySize > 1)
+ return true;
+ if (desc.ViewDimension == D3D11_RTV_DIMENSION_TEXTURE2DMSARRAY &&
+ desc.Texture2DMSArray.ArraySize > 1)
+ return true;
+ return false;
+}
+
+int GetAdjustedInstanceCount(const gl::Program *program, int instanceCount)
+{
+ if (!program->usesMultiview())
+ {
+ return instanceCount;
+ }
+ if (instanceCount == 0)
+ {
+ return program->getNumViews();
+ }
+ return program->getNumViews() * instanceCount;
+}
+
+const uint32_t ScratchMemoryBufferLifetime = 1000;
+
+void PopulateFormatDeviceCaps(ID3D11Device *device,
+ DXGI_FORMAT format,
+ UINT *outSupport,
+ UINT *outMaxSamples)
+{
+ if (FAILED(device->CheckFormatSupport(format, outSupport)))
+ {
+ *outSupport = 0;
+ }
+
+ *outMaxSamples = 0;
+ for (UINT sampleCount = 2; sampleCount <= D3D11_MAX_MULTISAMPLE_SAMPLE_COUNT; sampleCount *= 2)
+ {
+ UINT qualityCount = 0;
+ if (FAILED(device->CheckMultisampleQualityLevels(format, sampleCount, &qualityCount)) ||
+ qualityCount == 0)
+ {
+ break;
+ }
+
+ *outMaxSamples = sampleCount;
+ }
+}
+
+bool CullsEverything(const gl::State &glState)
+{
+ return (glState.getRasterizerState().cullFace &&
+ glState.getRasterizerState().cullMode == gl::CullFaceMode::FrontAndBack);
+}
+
} // anonymous namespace
+Renderer11DeviceCaps::Renderer11DeviceCaps() = default;
+
Renderer11::Renderer11(egl::Display *display)
: RendererD3D(display),
- mStateCache(this),
+ mCreateDebugDevice(false),
+ mStateCache(),
mStateManager(this),
- mLastHistogramUpdateTime(ANGLEPlatformCurrent()->monotonicallyIncreasingTime())
-#if !defined(ANGLE_MINGW32_COMPAT)
- ,mDebug(nullptr)
-#endif
+ mLastHistogramUpdateTime(
+ ANGLEPlatformCurrent()->monotonicallyIncreasingTime(ANGLEPlatformCurrent())),
+ mDebug(nullptr),
+ mScratchMemoryBuffer(ScratchMemoryBufferLifetime),
+ mAnnotator(nullptr)
{
- mVertexDataManager = NULL;
- mIndexDataManager = NULL;
+ mLineLoopIB = nullptr;
+ mTriangleFanIB = nullptr;
- mLineLoopIB = NULL;
- mTriangleFanIB = NULL;
- mAppliedIBChanged = false;
+ mBlit = nullptr;
+ mPixelTransfer = nullptr;
- mBlit = NULL;
- mPixelTransfer = NULL;
+ mClear = nullptr;
- mClear = NULL;
+ mTrim = nullptr;
- mTrim = NULL;
-
- mSyncQuery = NULL;
-
- mRenderer11DeviceCaps.supportsClearView = false;
+ mRenderer11DeviceCaps.supportsClearView = false;
mRenderer11DeviceCaps.supportsConstantBufferOffsets = false;
- mRenderer11DeviceCaps.supportsDXGI1_2 = false;
- mRenderer11DeviceCaps.B5G6R5support = 0;
- mRenderer11DeviceCaps.B4G4R4A4support = 0;
- mRenderer11DeviceCaps.B5G5R5A1support = 0;
-
- mD3d11Module = NULL;
- mDxgiModule = NULL;
- mDCompModule = NULL;
+ mRenderer11DeviceCaps.supportsVpRtIndexWriteFromVertexShader = false;
+ mRenderer11DeviceCaps.supportsDXGI1_2 = false;
+ mRenderer11DeviceCaps.B5G6R5support = 0;
+ mRenderer11DeviceCaps.B4G4R4A4support = 0;
+ mRenderer11DeviceCaps.B5G5R5A1support = 0;
+
+ mD3d11Module = nullptr;
+ mDxgiModule = nullptr;
+ mDCompModule = nullptr;
mCreatedWithDeviceEXT = false;
mEGLDevice = nullptr;
- mDevice = NULL;
- mDeviceContext = NULL;
- mDeviceContext1 = NULL;
- mDxgiAdapter = NULL;
- mDxgiFactory = NULL;
-
- mDriverConstantBufferVS = NULL;
- mDriverConstantBufferPS = NULL;
-
- mAppliedVertexShader = NULL;
- mAppliedGeometryShader = NULL;
- mAppliedPixelShader = NULL;
-
- mAppliedNumXFBBindings = static_cast<size_t>(-1);
+ mDevice = nullptr;
+ mDeviceContext = nullptr;
+ mDeviceContext1 = nullptr;
+ mDeviceContext3 = nullptr;
+ mDxgiAdapter = nullptr;
+ mDxgiFactory = nullptr;
ZeroMemory(&mAdapterDescription, sizeof(mAdapterDescription));
@@ -426,13 +488,21 @@ Renderer11::Renderer11(egl::Display *display)
{
const auto &attributes = mDisplay->getAttributeMap();
- EGLint requestedMajorVersion =
- attributes.get(EGL_PLATFORM_ANGLE_MAX_VERSION_MAJOR_ANGLE, EGL_DONT_CARE);
- EGLint requestedMinorVersion =
- attributes.get(EGL_PLATFORM_ANGLE_MAX_VERSION_MINOR_ANGLE, EGL_DONT_CARE);
+ EGLint requestedMajorVersion = static_cast<EGLint>(
+ attributes.get(EGL_PLATFORM_ANGLE_MAX_VERSION_MAJOR_ANGLE, EGL_DONT_CARE));
+ EGLint requestedMinorVersion = static_cast<EGLint>(
+ attributes.get(EGL_PLATFORM_ANGLE_MAX_VERSION_MINOR_ANGLE, EGL_DONT_CARE));
if (requestedMajorVersion == EGL_DONT_CARE || requestedMajorVersion >= 11)
{
+ if (requestedMinorVersion == EGL_DONT_CARE || requestedMinorVersion >= 1)
+ {
+ // This could potentially lead to failed context creation if done on a system
+ // without the platform update which installs DXGI 1.2. Currently, for Chrome users
+ // D3D11 contexts are only created if the platform update is available, so this
+ // should not cause any issues.
+ mAvailableFeatureLevels.push_back(D3D_FEATURE_LEVEL_11_1);
+ }
if (requestedMinorVersion == EGL_DONT_CARE || requestedMinorVersion >= 0)
{
mAvailableFeatureLevels.push_back(D3D_FEATURE_LEVEL_11_0);
@@ -451,11 +521,7 @@ Renderer11::Renderer11(egl::Display *display)
}
}
-#if defined(ANGLE_ENABLE_WINDOWS_STORE)
- if (requestedMajorVersion == EGL_DONT_CARE || requestedMajorVersion >= 9)
-#else
if (requestedMajorVersion == 9 && requestedMinorVersion == 3)
-#endif
{
if (requestedMinorVersion == EGL_DONT_CARE || requestedMinorVersion >= 3)
{
@@ -473,8 +539,8 @@ Renderer11::Renderer11(egl::Display *display)
#endif
}
- EGLint requestedDeviceType = attributes.get(EGL_PLATFORM_ANGLE_DEVICE_TYPE_ANGLE,
- EGL_PLATFORM_ANGLE_DEVICE_TYPE_HARDWARE_ANGLE);
+ EGLint requestedDeviceType = static_cast<EGLint>(attributes.get(
+ EGL_PLATFORM_ANGLE_DEVICE_TYPE_ANGLE, EGL_PLATFORM_ANGLE_DEVICE_TYPE_HARDWARE_ANGLE));
switch (requestedDeviceType)
{
case EGL_PLATFORM_ANGLE_DEVICE_TYPE_HARDWARE_ANGLE:
@@ -497,9 +563,11 @@ Renderer11::Renderer11(egl::Display *display)
UNREACHABLE();
}
- const EGLenum presentPath = attributes.get(EGL_EXPERIMENTAL_PRESENT_PATH_ANGLE,
- EGL_EXPERIMENTAL_PRESENT_PATH_COPY_ANGLE);
+ const EGLenum presentPath = static_cast<EGLenum>(attributes.get(
+ EGL_EXPERIMENTAL_PRESENT_PATH_ANGLE, EGL_EXPERIMENTAL_PRESENT_PATH_COPY_ANGLE));
mPresentPathFastEnabled = (presentPath == EGL_EXPERIMENTAL_PRESENT_PATH_FAST_ANGLE);
+
+ mCreateDebugDevice = ShouldUseDebugLayers(attributes);
}
else if (display->getPlatform() == EGL_PLATFORM_DEVICE_EXT)
{
@@ -509,11 +577,22 @@ Renderer11::Renderer11(egl::Display *display)
// Also set EGL_PLATFORM_ANGLE_ANGLE variables, in case they're used elsewhere in ANGLE
// mAvailableFeatureLevels defaults to empty
- mRequestedDriverType = D3D_DRIVER_TYPE_UNKNOWN;
+ mRequestedDriverType = D3D_DRIVER_TYPE_UNKNOWN;
mPresentPathFastEnabled = false;
}
- initializeDebugAnnotator();
+// The D3D11 renderer must choose the D3D9 debug annotator because the D3D11 interface
+// method ID3DUserDefinedAnnotation::GetStatus on desktop builds doesn't work with the Graphics
+// Diagnostics tools in Visual Studio 2013.
+// The D3D9 annotator works properly for both D3D11 and D3D9.
+// Incorrect status reporting can cause ANGLE to log unnecessary debug events.
+#ifdef ANGLE_ENABLE_D3D9
+ mAnnotator = new DebugAnnotator9();
+#else
+ mAnnotator = new DebugAnnotator11();
+#endif
+ ASSERT(mAnnotator);
+ gl::InitializeDebugAnnotations(mAnnotator);
}
Renderer11::~Renderer11()
@@ -529,20 +608,17 @@ egl::Error Renderer11::initialize()
{
HRESULT result = S_OK;
- egl::Error error = initializeD3DDevice();
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(initializeD3DDevice());
#if !defined(ANGLE_ENABLE_WINDOWS_STORE)
#if !ANGLE_SKIP_DXGI_1_2_CHECK
{
TRACE_EVENT0("gpu.angle", "Renderer11::initialize (DXGICheck)");
- // In order to create a swap chain for an HWND owned by another process, DXGI 1.2 is required.
+ // In order to create a swap chain for an HWND owned by another process, DXGI 1.2 is
+ // required.
// The easiest way to check is to query for a IDXGIDevice2.
bool requireDXGI1_2 = false;
- HWND hwnd = WindowFromDC(mDisplay->getNativeDisplayId());
+ HWND hwnd = WindowFromDC(mDisplay->getNativeDisplayId());
if (hwnd)
{
DWORD currentProcessId = GetCurrentProcessId();
@@ -557,13 +633,12 @@ egl::Error Renderer11::initialize()
if (requireDXGI1_2)
{
- IDXGIDevice2 *dxgiDevice2 = NULL;
- result = mDevice->QueryInterface(__uuidof(IDXGIDevice2), (void**)&dxgiDevice2);
+ IDXGIDevice2 *dxgiDevice2 = nullptr;
+ result = mDevice->QueryInterface(__uuidof(IDXGIDevice2), (void **)&dxgiDevice2);
if (FAILED(result))
{
- return egl::Error(EGL_NOT_INITIALIZED,
- D3D11_INIT_INCOMPATIBLE_DXGI,
- "DXGI 1.2 required to present to HWNDs owned by another process.");
+ return egl::EglNotInitialized(D3D11_INIT_INCOMPATIBLE_DXGI)
+ << "DXGI 1.2 required to present to HWNDs owned by another process.";
}
SafeRelease(dxgiDevice2);
}
@@ -573,90 +648,83 @@ egl::Error Renderer11::initialize()
{
TRACE_EVENT0("gpu.angle", "Renderer11::initialize (ComQueries)");
- // Cast the DeviceContext to a DeviceContext1.
+ // Cast the DeviceContext to a DeviceContext1 and DeviceContext3.
// This could fail on Windows 7 without the Platform Update.
- // Don't error in this case- just don't use mDeviceContext1.
-#if defined(ANGLE_ENABLE_D3D11_1)
+ // Don't error in this case- just don't use mDeviceContext1 or mDeviceContext3.
mDeviceContext1 = d3d11::DynamicCastComObject<ID3D11DeviceContext1>(mDeviceContext);
-#endif
+ mDeviceContext3 = d3d11::DynamicCastComObject<ID3D11DeviceContext3>(mDeviceContext);
- IDXGIDevice *dxgiDevice = NULL;
- result = mDevice->QueryInterface(__uuidof(IDXGIDevice), (void**)&dxgiDevice);
+ IDXGIDevice *dxgiDevice = nullptr;
+ result = mDevice->QueryInterface(__uuidof(IDXGIDevice), (void **)&dxgiDevice);
if (FAILED(result))
{
- return egl::Error(EGL_NOT_INITIALIZED,
- D3D11_INIT_OTHER_ERROR,
- "Could not query DXGI device.");
+ return egl::EglNotInitialized(D3D11_INIT_OTHER_ERROR) << "Could not query DXGI device.";
}
- result = dxgiDevice->GetParent(__uuidof(IDXGIAdapter), (void**)&mDxgiAdapter);
+ result = dxgiDevice->GetParent(__uuidof(IDXGIAdapter), (void **)&mDxgiAdapter);
if (FAILED(result))
{
- return egl::Error(EGL_NOT_INITIALIZED,
- D3D11_INIT_OTHER_ERROR,
- "Could not retrieve DXGI adapter");
+ return egl::EglNotInitialized(D3D11_INIT_OTHER_ERROR)
+ << "Could not retrieve DXGI adapter";
}
SafeRelease(dxgiDevice);
-#if defined(ANGLE_ENABLE_D3D11_1)
IDXGIAdapter2 *dxgiAdapter2 = d3d11::DynamicCastComObject<IDXGIAdapter2>(mDxgiAdapter);
- // On D3D_FEATURE_LEVEL_9_*, IDXGIAdapter::GetDesc returns "Software Adapter" for the description string.
- // If DXGI1.2 is available then IDXGIAdapter2::GetDesc2 can be used to get the actual hardware values.
- if (mRenderer11DeviceCaps.featureLevel <= D3D_FEATURE_LEVEL_9_3 && dxgiAdapter2 != NULL)
+ // On D3D_FEATURE_LEVEL_9_*, IDXGIAdapter::GetDesc returns "Software Adapter" for the
+ // description string.
+ // If DXGI1.2 is available then IDXGIAdapter2::GetDesc2 can be used to get the actual
+ // hardware values.
+ if (mRenderer11DeviceCaps.featureLevel <= D3D_FEATURE_LEVEL_9_3 && dxgiAdapter2 != nullptr)
{
DXGI_ADAPTER_DESC2 adapterDesc2 = {};
- result = dxgiAdapter2->GetDesc2(&adapterDesc2);
+ result = dxgiAdapter2->GetDesc2(&adapterDesc2);
if (SUCCEEDED(result))
{
- // Copy the contents of the DXGI_ADAPTER_DESC2 into mAdapterDescription (a DXGI_ADAPTER_DESC).
- memcpy(mAdapterDescription.Description, adapterDesc2.Description, sizeof(mAdapterDescription.Description));
- mAdapterDescription.VendorId = adapterDesc2.VendorId;
- mAdapterDescription.DeviceId = adapterDesc2.DeviceId;
- mAdapterDescription.SubSysId = adapterDesc2.SubSysId;
- mAdapterDescription.Revision = adapterDesc2.Revision;
- mAdapterDescription.DedicatedVideoMemory = adapterDesc2.DedicatedVideoMemory;
+ // Copy the contents of the DXGI_ADAPTER_DESC2 into mAdapterDescription (a
+ // DXGI_ADAPTER_DESC).
+ memcpy(mAdapterDescription.Description, adapterDesc2.Description,
+ sizeof(mAdapterDescription.Description));
+ mAdapterDescription.VendorId = adapterDesc2.VendorId;
+ mAdapterDescription.DeviceId = adapterDesc2.DeviceId;
+ mAdapterDescription.SubSysId = adapterDesc2.SubSysId;
+ mAdapterDescription.Revision = adapterDesc2.Revision;
+ mAdapterDescription.DedicatedVideoMemory = adapterDesc2.DedicatedVideoMemory;
mAdapterDescription.DedicatedSystemMemory = adapterDesc2.DedicatedSystemMemory;
- mAdapterDescription.SharedSystemMemory = adapterDesc2.SharedSystemMemory;
- mAdapterDescription.AdapterLuid = adapterDesc2.AdapterLuid;
+ mAdapterDescription.SharedSystemMemory = adapterDesc2.SharedSystemMemory;
+ mAdapterDescription.AdapterLuid = adapterDesc2.AdapterLuid;
}
}
else
-#endif
{
result = mDxgiAdapter->GetDesc(&mAdapterDescription);
}
-#if defined(ANGLE_ENABLE_D3D11_1)
SafeRelease(dxgiAdapter2);
-#endif
if (FAILED(result))
{
- return egl::Error(EGL_NOT_INITIALIZED,
- D3D11_INIT_OTHER_ERROR,
- "Could not read DXGI adaptor description.");
+ return egl::EglNotInitialized(D3D11_INIT_OTHER_ERROR)
+ << "Could not read DXGI adaptor description.";
}
memset(mDescription, 0, sizeof(mDescription));
wcstombs(mDescription, mAdapterDescription.Description, sizeof(mDescription) - 1);
- result = mDxgiAdapter->GetParent(__uuidof(IDXGIFactory), (void**)&mDxgiFactory);
+ result = mDxgiAdapter->GetParent(__uuidof(IDXGIFactory), (void **)&mDxgiFactory);
if (!mDxgiFactory || FAILED(result))
{
- return egl::Error(EGL_NOT_INITIALIZED,
- D3D11_INIT_OTHER_ERROR,
- "Could not create DXGI factory.");
+ return egl::EglNotInitialized(D3D11_INIT_OTHER_ERROR)
+ << "Could not create DXGI factory.";
}
}
-#if !defined(ANGLE_MINGW32_COMPAT)
// Disable some spurious D3D11 debug warnings to prevent them from flooding the output log
-#if defined(ANGLE_SUPPRESS_D3D11_HAZARD_WARNINGS) && defined(_DEBUG)
+ if (mCreateDebugDevice)
{
TRACE_EVENT0("gpu.angle", "Renderer11::initialize (HideWarnings)");
ID3D11InfoQueue *infoQueue;
@@ -664,29 +732,33 @@ egl::Error Renderer11::initialize()
if (SUCCEEDED(result))
{
- D3D11_MESSAGE_ID hideMessages[] =
- {
- D3D11_MESSAGE_ID_DEVICE_DRAW_RENDERTARGETVIEW_NOT_SET
- };
+ D3D11_MESSAGE_ID hideMessages[] = {
+ D3D11_MESSAGE_ID_DEVICE_DRAW_RENDERTARGETVIEW_NOT_SET};
D3D11_INFO_QUEUE_FILTER filter = {};
filter.DenyList.NumIDs = static_cast<unsigned int>(ArraySize(hideMessages));
- filter.DenyList.pIDList = hideMessages;
+ filter.DenyList.pIDList = hideMessages;
infoQueue->AddStorageFilterEntries(&filter);
SafeRelease(infoQueue);
}
}
-#endif
#if !defined(NDEBUG)
mDebug = d3d11::DynamicCastComObject<ID3D11Debug>(mDevice);
#endif
-#endif // !ANGLE_MINGW32_COMPAT
- initializeDevice();
+ ANGLE_TRY(initializeDevice());
+
+ return egl::NoError();
+}
- return egl::Error(EGL_SUCCESS);
+HRESULT Renderer11::callD3D11CreateDevice(PFN_D3D11_CREATE_DEVICE createDevice, bool debug)
+{
+ return createDevice(
+ nullptr, mRequestedDriverType, nullptr, debug ? D3D11_CREATE_DEVICE_DEBUG : 0,
+ mAvailableFeatureLevels.data(), static_cast<unsigned int>(mAvailableFeatureLevels.size()),
+ D3D11_SDK_VERSION, &mDevice, &(mRenderer11DeviceCaps.featureLevel), &mDeviceContext);
}
egl::Error Renderer11::initializeD3DDevice()
@@ -706,8 +778,8 @@ egl::Error Renderer11::initializeD3DDevice()
if (mD3d11Module == nullptr || mDxgiModule == nullptr)
{
- return egl::Error(EGL_NOT_INITIALIZED, D3D11_INIT_MISSING_DEP,
- "Could not load D3D11 or DXGI library.");
+ return egl::EglNotInitialized(D3D11_INIT_MISSING_DEP)
+ << "Could not load D3D11 or DXGI library.";
}
// create the D3D11 device
@@ -717,68 +789,76 @@ egl::Error Renderer11::initializeD3DDevice()
if (D3D11CreateDevice == nullptr)
{
- return egl::Error(EGL_NOT_INITIALIZED, D3D11_INIT_MISSING_DEP,
- "Could not retrieve D3D11CreateDevice address.");
+ return egl::EglNotInitialized(D3D11_INIT_MISSING_DEP)
+ << "Could not retrieve D3D11CreateDevice address.";
}
}
#endif
-#ifdef _DEBUG
+ if (mCreateDebugDevice)
{
TRACE_EVENT0("gpu.angle", "D3D11CreateDevice (Debug)");
- result = D3D11CreateDevice(nullptr, mRequestedDriverType, nullptr,
- D3D11_CREATE_DEVICE_DEBUG, mAvailableFeatureLevels.data(),
- static_cast<unsigned int>(mAvailableFeatureLevels.size()),
- D3D11_SDK_VERSION, &mDevice,
- &(mRenderer11DeviceCaps.featureLevel), &mDeviceContext);
- }
+ result = callD3D11CreateDevice(D3D11CreateDevice, true);
- if (!mDevice || FAILED(result))
- {
- ERR("Failed creating Debug D3D11 device - falling back to release runtime.\n");
+ if (result == E_INVALIDARG && mAvailableFeatureLevels.size() > 1u &&
+ mAvailableFeatureLevels[0] == D3D_FEATURE_LEVEL_11_1)
+ {
+ // On older Windows platforms, D3D11.1 is not supported which returns E_INVALIDARG.
+ // Try again without passing D3D_FEATURE_LEVEL_11_1 in case we have other feature
+ // levels to fall back on.
+ mAvailableFeatureLevels.erase(mAvailableFeatureLevels.begin());
+ result = callD3D11CreateDevice(D3D11CreateDevice, true);
+ }
+
+ if (!mDevice || FAILED(result))
+ {
+ WARN() << "Failed creating Debug D3D11 device - falling back to release runtime.";
+ }
}
if (!mDevice || FAILED(result))
-#endif
{
SCOPED_ANGLE_HISTOGRAM_TIMER("GPU.ANGLE.D3D11CreateDeviceMS");
TRACE_EVENT0("gpu.angle", "D3D11CreateDevice");
- result = D3D11CreateDevice(
- nullptr, mRequestedDriverType, nullptr, 0, mAvailableFeatureLevels.data(),
- static_cast<unsigned int>(mAvailableFeatureLevels.size()), D3D11_SDK_VERSION,
- &mDevice, &(mRenderer11DeviceCaps.featureLevel), &mDeviceContext);
+ result = callD3D11CreateDevice(D3D11CreateDevice, false);
+
+ if (result == E_INVALIDARG && mAvailableFeatureLevels.size() > 1u &&
+ mAvailableFeatureLevels[0] == D3D_FEATURE_LEVEL_11_1)
+ {
+ // On older Windows platforms, D3D11.1 is not supported which returns E_INVALIDARG.
+ // Try again without passing D3D_FEATURE_LEVEL_11_1 in case we have other feature
+ // levels to fall back on.
+ mAvailableFeatureLevels.erase(mAvailableFeatureLevels.begin());
+ result = callD3D11CreateDevice(D3D11CreateDevice, false);
+ }
// Cleanup done by destructor
if (!mDevice || FAILED(result))
{
ANGLE_HISTOGRAM_SPARSE_SLOWLY("GPU.ANGLE.D3D11CreateDeviceError",
static_cast<int>(result));
- return egl::Error(EGL_NOT_INITIALIZED, D3D11_INIT_CREATEDEVICE_ERROR,
- "Could not create D3D11 device.");
+ return egl::EglNotInitialized(D3D11_INIT_CREATEDEVICE_ERROR)
+ << "Could not create D3D11 device.";
}
}
}
else
{
// We should use the inputted D3D11 device instead
- void *device = nullptr;
- egl::Error error = mEGLDevice->getDevice(&device);
- if (error.isError())
- {
- return error;
- }
+ void *device = nullptr;
+ ANGLE_TRY(mEGLDevice->getDevice(&device));
ID3D11Device *d3dDevice = reinterpret_cast<ID3D11Device *>(device);
if (FAILED(d3dDevice->GetDeviceRemovedReason()))
{
- return egl::Error(EGL_NOT_INITIALIZED, "Inputted D3D11 device has been lost.");
+ return egl::EglNotInitialized() << "Inputted D3D11 device has been lost.";
}
if (d3dDevice->GetFeatureLevel() < D3D_FEATURE_LEVEL_9_3)
{
- return egl::Error(EGL_NOT_INITIALIZED,
- "Inputted D3D11 device must be Feature Level 9_3 or greater.");
+ return egl::EglNotInitialized()
+ << "Inputted D3D11 device must be Feature Level 9_3 or greater.";
}
// The Renderer11 adds a ref to the inputted D3D11 device, like D3D11CreateDevice does.
@@ -788,27 +868,24 @@ egl::Error Renderer11::initializeD3DDevice()
mRenderer11DeviceCaps.featureLevel = mDevice->GetFeatureLevel();
}
+ mResourceManager11.setAllocationsInitialized(mCreateDebugDevice);
+
d3d11::SetDebugName(mDeviceContext, "DeviceContext");
- return egl::Error(EGL_SUCCESS);
+ return egl::NoError();
}
// do any one-time device initialization
// NOTE: this is also needed after a device lost/reset
// to reset the scene status and ensure the default states are reset.
-void Renderer11::initializeDevice()
+egl::Error Renderer11::initializeDevice()
{
SCOPED_ANGLE_HISTOGRAM_TIMER("GPU.ANGLE.Renderer11InitializeDeviceMS");
TRACE_EVENT0("gpu.angle", "Renderer11::initializeDevice");
populateRenderer11DeviceCaps();
- mStateCache.initialize(mDevice);
- mInputLayoutCache.initialize(mDevice, mDeviceContext);
-
- ASSERT(!mVertexDataManager && !mIndexDataManager);
- mVertexDataManager = new VertexDataManager(this);
- mIndexDataManager = new IndexDataManager(this, getRendererClass());
+ mStateCache.clear();
ASSERT(!mBlit);
mBlit = new Blit11(this);
@@ -820,7 +897,8 @@ void Renderer11::initializeDevice()
// If automatic trim is enabled, DXGIDevice3::Trim( ) is called for the application
// automatically when an application is suspended by the OS. This feature is currently
// only supported for Windows Store applications.
- EGLint enableAutoTrim = attributes.get(EGL_PLATFORM_ANGLE_ENABLE_AUTOMATIC_TRIM_ANGLE, EGL_FALSE);
+ EGLint enableAutoTrim = static_cast<EGLint>(
+ attributes.get(EGL_PLATFORM_ANGLE_ENABLE_AUTOMATIC_TRIM_ANGLE, EGL_FALSE));
if (enableAutoTrim == EGL_TRUE)
{
@@ -831,19 +909,12 @@ void Renderer11::initializeDevice()
ASSERT(!mPixelTransfer);
mPixelTransfer = new PixelTransfer11(this);
- const gl::Caps &rendererCaps = getRendererCaps();
-
- mStateManager.initialize(rendererCaps);
-
- mForceSetVertexSamplerStates.resize(rendererCaps.maxVertexTextureImageUnits);
- mCurVertexSamplerStates.resize(rendererCaps.maxVertexTextureImageUnits);
-
- mForceSetPixelSamplerStates.resize(rendererCaps.maxTextureImageUnits);
- mCurPixelSamplerStates.resize(rendererCaps.maxTextureImageUnits);
-
- mStateManager.initialize(rendererCaps);
+ const gl::Caps &rendererCaps = getNativeCaps();
- markAllStateDirty();
+ if (mStateManager.initialize(rendererCaps, getNativeExtensions()).isError())
+ {
+ return egl::EglBadAlloc() << "Error initializing state manager.";
+ }
// Gather stats on DXGI and D3D feature level
ANGLE_HISTOGRAM_BOOLEAN("GPU.ANGLE.SupportsDXGI1_2", mRenderer11DeviceCaps.supportsDXGI1_2);
@@ -859,57 +930,117 @@ void Renderer11::initializeDevice()
angleFeatureLevel = ANGLE_FEATURE_LEVEL_11_1;
}
- ANGLE_HISTOGRAM_ENUMERATION("GPU.ANGLE.D3D11FeatureLevel",
- angleFeatureLevel,
+ ANGLE_HISTOGRAM_ENUMERATION("GPU.ANGLE.D3D11FeatureLevel", angleFeatureLevel,
NUM_ANGLE_FEATURE_LEVELS);
- // TODO(jmadill): use context caps, and place in common D3D location
- mTranslatedAttribCache.resize(getRendererCaps().maxVertexAttributes);
+ return egl::NoError();
}
void Renderer11::populateRenderer11DeviceCaps()
{
HRESULT hr = S_OK;
-#if defined(ANGLE_ENABLE_D3D11_1)
+ LARGE_INTEGER version;
+ hr = mDxgiAdapter->CheckInterfaceSupport(__uuidof(IDXGIDevice), &version);
+ if (FAILED(hr))
+ {
+ mRenderer11DeviceCaps.driverVersion.reset();
+ ERR() << "Error querying driver version from DXGI Adapter.";
+ }
+ else
+ {
+ mRenderer11DeviceCaps.driverVersion = version;
+ }
+
if (mDeviceContext1)
{
D3D11_FEATURE_DATA_D3D11_OPTIONS d3d11Options;
- HRESULT result = mDevice->CheckFeatureSupport(D3D11_FEATURE_D3D11_OPTIONS, &d3d11Options, sizeof(D3D11_FEATURE_DATA_D3D11_OPTIONS));
+ HRESULT result = mDevice->CheckFeatureSupport(D3D11_FEATURE_D3D11_OPTIONS, &d3d11Options,
+ sizeof(D3D11_FEATURE_DATA_D3D11_OPTIONS));
if (SUCCEEDED(result))
{
mRenderer11DeviceCaps.supportsClearView = (d3d11Options.ClearView != FALSE);
- mRenderer11DeviceCaps.supportsConstantBufferOffsets = (d3d11Options.ConstantBufferOffsetting != FALSE);
+ mRenderer11DeviceCaps.supportsConstantBufferOffsets =
+ (d3d11Options.ConstantBufferOffsetting != FALSE);
}
}
-#endif
- hr = mDevice->CheckFormatSupport(DXGI_FORMAT_B5G6R5_UNORM, &(mRenderer11DeviceCaps.B5G6R5support));
- if (FAILED(hr))
+ if (mDeviceContext3)
{
- mRenderer11DeviceCaps.B5G6R5support = 0;
+ D3D11_FEATURE_DATA_D3D11_OPTIONS3 d3d11Options3;
+ HRESULT result = mDevice->CheckFeatureSupport(D3D11_FEATURE_D3D11_OPTIONS3, &d3d11Options3,
+ sizeof(D3D11_FEATURE_DATA_D3D11_OPTIONS3));
+ if (SUCCEEDED(result))
+ {
+ mRenderer11DeviceCaps.supportsVpRtIndexWriteFromVertexShader =
+ (d3d11Options3.VPAndRTArrayIndexFromAnyShaderFeedingRasterizer == TRUE);
+ }
}
- hr = mDevice->CheckFormatSupport(DXGI_FORMAT_B4G4R4A4_UNORM, &(mRenderer11DeviceCaps.B4G4R4A4support));
- if (FAILED(hr))
+ mRenderer11DeviceCaps.supportsMultisampledDepthStencilSRVs =
+ mRenderer11DeviceCaps.featureLevel > D3D_FEATURE_LEVEL_10_0;
+
+ if (getWorkarounds().disableB5G6R5Support)
{
- mRenderer11DeviceCaps.B4G4R4A4support = 0;
+ mRenderer11DeviceCaps.B5G6R5support = 0;
+ mRenderer11DeviceCaps.B5G6R5maxSamples = 0;
}
-
- hr = mDevice->CheckFormatSupport(DXGI_FORMAT_B5G5R5A1_UNORM, &(mRenderer11DeviceCaps.B5G5R5A1support));
- if (FAILED(hr))
+ else
{
- mRenderer11DeviceCaps.B5G5R5A1support = 0;
+ PopulateFormatDeviceCaps(mDevice, DXGI_FORMAT_B5G6R5_UNORM,
+ &mRenderer11DeviceCaps.B5G6R5support,
+ &mRenderer11DeviceCaps.B5G6R5maxSamples);
}
-#if defined(ANGLE_ENABLE_D3D11_1)
+ PopulateFormatDeviceCaps(mDevice, DXGI_FORMAT_B4G4R4A4_UNORM,
+ &mRenderer11DeviceCaps.B4G4R4A4support,
+ &mRenderer11DeviceCaps.B4G4R4A4maxSamples);
+ PopulateFormatDeviceCaps(mDevice, DXGI_FORMAT_B5G5R5A1_UNORM,
+ &mRenderer11DeviceCaps.B5G5R5A1support,
+ &mRenderer11DeviceCaps.B5G5R5A1maxSamples);
+
IDXGIAdapter2 *dxgiAdapter2 = d3d11::DynamicCastComObject<IDXGIAdapter2>(mDxgiAdapter);
mRenderer11DeviceCaps.supportsDXGI1_2 = (dxgiAdapter2 != nullptr);
SafeRelease(dxgiAdapter2);
+}
+
+gl::SupportedSampleSet Renderer11::generateSampleSetForEGLConfig(
+ const gl::TextureCaps &colorBufferFormatCaps,
+ const gl::TextureCaps &depthStencilBufferFormatCaps) const
+{
+ gl::SupportedSampleSet sampleCounts;
+
+#if 0 // Disabling support for multisampling with Qt5 as it's causing a crash in the D3D11 shaders.
+
+ // Generate a new set from the set intersection of sample counts between the color and depth
+ // format caps.
+ std::set_intersection(colorBufferFormatCaps.sampleCounts.begin(),
+ colorBufferFormatCaps.sampleCounts.end(),
+ depthStencilBufferFormatCaps.sampleCounts.begin(),
+ depthStencilBufferFormatCaps.sampleCounts.end(),
+ std::inserter(sampleCounts, sampleCounts.begin()));
+
+ // Format of GL_NONE results in no supported sample counts.
+ // Add back the color sample counts to the supported sample set.
+ if (depthStencilBufferFormatCaps.sampleCounts.empty())
+ {
+ sampleCounts = colorBufferFormatCaps.sampleCounts;
+ }
+ else if (colorBufferFormatCaps.sampleCounts.empty())
+ {
+ // Likewise, add back the depth sample counts to the supported sample set.
+ sampleCounts = depthStencilBufferFormatCaps.sampleCounts;
+ }
+
#endif
+
+ // Always support 0 samples
+ sampleCounts.insert(0);
+
+ return sampleCounts;
}
-egl::ConfigSet Renderer11::generateConfigs() const
+egl::ConfigSet Renderer11::generateConfigs()
{
std::vector<GLenum> colorBufferFormats;
@@ -920,6 +1051,14 @@ egl::ConfigSet Renderer11::generateConfigs() const
// 24-bit supported formats
colorBufferFormats.push_back(GL_RGB8_OES);
+ if (mRenderer11DeviceCaps.featureLevel >= D3D_FEATURE_LEVEL_10_0)
+ {
+ // Additional high bit depth formats added in D3D 10.0
+ // https://msdn.microsoft.com/en-us/library/windows/desktop/bb173064.aspx
+ colorBufferFormats.push_back(GL_RGBA16F);
+ colorBufferFormats.push_back(GL_RGB10_A2);
+ }
+
if (!mPresentPathFastEnabled)
{
// 16-bit supported formats
@@ -930,15 +1069,13 @@ egl::ConfigSet Renderer11::generateConfigs() const
colorBufferFormats.push_back(GL_RGB565);
}
- static const GLenum depthStencilBufferFormats[] =
- {
- GL_NONE,
- GL_DEPTH24_STENCIL8_OES,
- GL_DEPTH_COMPONENT16,
+ static const GLenum depthStencilBufferFormats[] = {
+ GL_NONE, GL_DEPTH24_STENCIL8_OES, GL_DEPTH_COMPONENT24, GL_DEPTH_COMPONENT16,
+ GL_STENCIL_INDEX8,
};
- const gl::Caps &rendererCaps = getRendererCaps();
- const gl::TextureCapsMap &rendererTextureCaps = getRendererTextureCaps();
+ const gl::Caps &rendererCaps = getNativeCaps();
+ const gl::TextureCapsMap &rendererTextureCaps = getNativeTextureCaps();
const EGLint optimalSurfaceOrientation =
mPresentPathFastEnabled ? 0 : EGL_SURFACE_ORIENTATION_INVERT_Y_ANGLE;
@@ -946,7 +1083,8 @@ egl::ConfigSet Renderer11::generateConfigs() const
egl::ConfigSet configs;
for (GLenum colorBufferInternalFormat : colorBufferFormats)
{
- const gl::TextureCaps &colorBufferFormatCaps = rendererTextureCaps.get(colorBufferInternalFormat);
+ const gl::TextureCaps &colorBufferFormatCaps =
+ rendererTextureCaps.get(colorBufferInternalFormat);
if (!colorBufferFormatCaps.renderable)
{
continue;
@@ -963,64 +1101,87 @@ egl::ConfigSet Renderer11::generateConfigs() const
}
const gl::InternalFormat &colorBufferFormatInfo =
- gl::GetInternalFormatInfo(colorBufferInternalFormat);
+ gl::GetSizedInternalFormatInfo(colorBufferInternalFormat);
const gl::InternalFormat &depthStencilBufferFormatInfo =
- gl::GetInternalFormatInfo(depthStencilBufferInternalFormat);
-
- egl::Config config;
- config.renderTargetFormat = colorBufferInternalFormat;
- config.depthStencilFormat = depthStencilBufferInternalFormat;
- config.bufferSize = colorBufferFormatInfo.pixelBytes * 8;
- config.redSize = colorBufferFormatInfo.redBits;
- config.greenSize = colorBufferFormatInfo.greenBits;
- config.blueSize = colorBufferFormatInfo.blueBits;
- config.luminanceSize = colorBufferFormatInfo.luminanceBits;
- config.alphaSize = colorBufferFormatInfo.alphaBits;
- config.alphaMaskSize = 0;
- config.bindToTextureRGB = (colorBufferFormatInfo.format == GL_RGB);
- config.bindToTextureRGBA = (colorBufferFormatInfo.format == GL_RGBA ||
- colorBufferFormatInfo.format == GL_BGRA_EXT);
- config.colorBufferType = EGL_RGB_BUFFER;
- config.configID = static_cast<EGLint>(configs.size() + 1);
- // Can only support a conformant ES2 with feature level greater than 10.0.
- config.conformant = (mRenderer11DeviceCaps.featureLevel >= D3D_FEATURE_LEVEL_10_0)
- ? (EGL_OPENGL_ES2_BIT | EGL_OPENGL_ES3_BIT_KHR)
- : 0;
- config.configCaveat = config.conformant == EGL_NONE ? EGL_NON_CONFORMANT_CONFIG : EGL_NONE;
-
- // PresentPathFast may not be conformant
- if (mPresentPathFastEnabled)
+ gl::GetSizedInternalFormatInfo(depthStencilBufferInternalFormat);
+ const gl::Version &maxVersion = getMaxSupportedESVersion();
+
+ const gl::SupportedSampleSet sampleCounts =
+ generateSampleSetForEGLConfig(colorBufferFormatCaps, depthStencilBufferFormatCaps);
+
+ for (GLuint sampleCount : sampleCounts)
{
+ egl::Config config;
+ config.renderTargetFormat = colorBufferInternalFormat;
+ config.depthStencilFormat = depthStencilBufferInternalFormat;
+ config.bufferSize = colorBufferFormatInfo.pixelBytes * 8;
+ config.redSize = colorBufferFormatInfo.redBits;
+ config.greenSize = colorBufferFormatInfo.greenBits;
+ config.blueSize = colorBufferFormatInfo.blueBits;
+ config.luminanceSize = colorBufferFormatInfo.luminanceBits;
+ config.alphaSize = colorBufferFormatInfo.alphaBits;
+ config.alphaMaskSize = 0;
+ config.bindToTextureRGB =
+ ((colorBufferFormatInfo.format == GL_RGB) && (sampleCount <= 1));
+ config.bindToTextureRGBA = (((colorBufferFormatInfo.format == GL_RGBA) ||
+ (colorBufferFormatInfo.format == GL_BGRA_EXT)) &&
+ (sampleCount <= 1));
+ config.colorBufferType = EGL_RGB_BUFFER;
+ config.configCaveat = EGL_NONE;
+ config.configID = static_cast<EGLint>(configs.size() + 1);
+
+ // PresentPathFast may not be conformant
config.conformant = 0;
- }
+ if (!mPresentPathFastEnabled)
+ {
+ // Can only support a conformant ES2 with feature level greater than 10.0.
+ if (mRenderer11DeviceCaps.featureLevel >= D3D_FEATURE_LEVEL_10_0)
+ {
+ config.conformant |= EGL_OPENGL_ES2_BIT;
+ }
+
+ // We can only support conformant ES3 on FL 10.1+
+ if (maxVersion.major >= 3)
+ {
+ config.conformant |= EGL_OPENGL_ES3_BIT_KHR;
+ }
+ }
+
+ config.depthSize = depthStencilBufferFormatInfo.depthBits;
+ config.level = 0;
+ config.matchNativePixmap = EGL_NONE;
+ config.maxPBufferWidth = rendererCaps.max2DTextureSize;
+ config.maxPBufferHeight = rendererCaps.max2DTextureSize;
+ config.maxPBufferPixels =
+ rendererCaps.max2DTextureSize * rendererCaps.max2DTextureSize;
+ config.maxSwapInterval = 4;
+ config.minSwapInterval = 0;
+ config.nativeRenderable = EGL_FALSE;
+ config.nativeVisualID = 0;
+ config.nativeVisualType = EGL_NONE;
+
+ // Can't support ES3 at all without feature level 10.1
+ config.renderableType = EGL_OPENGL_ES2_BIT;
+ if (maxVersion.major >= 3)
+ {
+ config.renderableType |= EGL_OPENGL_ES3_BIT_KHR;
+ }
- config.depthSize = depthStencilBufferFormatInfo.depthBits;
- config.level = 0;
- config.matchNativePixmap = EGL_NONE;
- config.maxPBufferWidth = rendererCaps.max2DTextureSize;
- config.maxPBufferHeight = rendererCaps.max2DTextureSize;
- config.maxPBufferPixels = rendererCaps.max2DTextureSize * rendererCaps.max2DTextureSize;
- config.maxSwapInterval = 4;
- config.minSwapInterval = 0;
- config.nativeRenderable = EGL_FALSE;
- config.nativeVisualID = 0;
- config.nativeVisualType = EGL_NONE;
- // Can't support ES3 at all without feature level 10.0
- config.renderableType =
- EGL_OPENGL_ES2_BIT | ((mRenderer11DeviceCaps.featureLevel >= D3D_FEATURE_LEVEL_10_0)
- ? EGL_OPENGL_ES3_BIT_KHR
- : 0);
- config.sampleBuffers = 0; // FIXME: enumerate multi-sampling
- config.samples = 0;
- config.stencilSize = depthStencilBufferFormatInfo.stencilBits;
- config.surfaceType = EGL_PBUFFER_BIT | EGL_WINDOW_BIT | EGL_SWAP_BEHAVIOR_PRESERVED_BIT;
- config.transparentType = EGL_NONE;
- config.transparentRedValue = 0;
- config.transparentGreenValue = 0;
- config.transparentBlueValue = 0;
- config.optimalOrientation = optimalSurfaceOrientation;
-
- configs.add(config);
+ config.sampleBuffers = (sampleCount == 0) ? 0 : 1;
+ config.samples = sampleCount;
+ config.stencilSize = depthStencilBufferFormatInfo.stencilBits;
+ config.surfaceType =
+ EGL_PBUFFER_BIT | EGL_WINDOW_BIT | EGL_SWAP_BEHAVIOR_PRESERVED_BIT;
+ config.transparentType = EGL_NONE;
+ config.transparentRedValue = 0;
+ config.transparentGreenValue = 0;
+ config.transparentBlueValue = 0;
+ config.optimalOrientation = optimalSurfaceOrientation;
+ config.colorComponentType = gl_egl::GLComponentTypeToEGLColorComponentType(
+ colorBufferFormatInfo.componentType);
+
+ configs.add(config);
+ }
}
}
@@ -1037,8 +1198,9 @@ void Renderer11::generateDisplayExtensions(egl::DisplayExtensions *outExtensions
outExtensions->d3dShareHandleClientBuffer = true;
outExtensions->surfaceD3DTexture2DShareHandle = true;
}
+ outExtensions->d3dTextureClientBuffer = true;
- outExtensions->keyedMutex = true;
+ outExtensions->keyedMutex = true;
outExtensions->querySurfacePointer = true;
outExtensions->windowFixedSize = true;
@@ -1048,624 +1210,350 @@ void Renderer11::generateDisplayExtensions(egl::DisplayExtensions *outExtensions
// D3D11 does not support present with dirty rectangles until DXGI 1.2.
outExtensions->postSubBuffer = mRenderer11DeviceCaps.supportsDXGI1_2;
- outExtensions->createContext = true;
-
outExtensions->deviceQuery = true;
- outExtensions->createContextNoError = true;
-
outExtensions->image = true;
outExtensions->imageBase = true;
outExtensions->glTexture2DImage = true;
outExtensions->glTextureCubemapImage = true;
outExtensions->glRenderbufferImage = true;
+ outExtensions->stream = true;
+ outExtensions->streamConsumerGLTexture = true;
+ outExtensions->streamConsumerGLTextureYUV = true;
+ // Not all D3D11 devices support NV12 textures
+ if (getNV12TextureSupport())
+ {
+ outExtensions->streamProducerD3DTextureNV12 = true;
+ }
+
outExtensions->flexibleSurfaceCompatibility = true;
outExtensions->directComposition = !!mDCompModule;
+
+ // Contexts are virtualized so textures can be shared globally
+ outExtensions->displayTextureShareGroup = true;
+
+ // getSyncValues requires direct composition.
+ outExtensions->getSyncValues = outExtensions->directComposition;
+
+ // D3D11 can be used without a swap chain
+ outExtensions->surfacelessContext = true;
+
+ // All D3D feature levels support robust resource init
+ outExtensions->robustResourceInitialization = true;
}
gl::Error Renderer11::flush()
{
mDeviceContext->Flush();
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
gl::Error Renderer11::finish()
{
- HRESULT result;
-
- if (!mSyncQuery)
+ if (!mSyncQuery.valid())
{
D3D11_QUERY_DESC queryDesc;
- queryDesc.Query = D3D11_QUERY_EVENT;
+ queryDesc.Query = D3D11_QUERY_EVENT;
queryDesc.MiscFlags = 0;
- result = mDevice->CreateQuery(&queryDesc, &mSyncQuery);
- ASSERT(SUCCEEDED(result));
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create event query, result: 0x%X.", result);
- }
+ ANGLE_TRY(allocateResource(queryDesc, &mSyncQuery));
}
- mDeviceContext->End(mSyncQuery);
- mDeviceContext->Flush();
+ mDeviceContext->End(mSyncQuery.get());
+ HRESULT result = S_OK;
+ unsigned int attempt = 0;
do
{
- result = mDeviceContext->GetData(mSyncQuery, NULL, 0, D3D11_ASYNC_GETDATA_DONOTFLUSH);
+ unsigned int flushFrequency = 100;
+ UINT flags = (attempt % flushFrequency == 0) ? 0 : D3D11_ASYNC_GETDATA_DONOTFLUSH;
+ attempt++;
+
+ result = mDeviceContext->GetData(mSyncQuery.get(), nullptr, 0, flags);
if (FAILED(result))
{
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to get event query data, result: 0x%X.", result);
+ return gl::OutOfMemory() << "Failed to get event query data, " << gl::FmtHR(result);
}
- // Keep polling, but allow other threads to do something useful first
- ScheduleYield();
+ if (result == S_FALSE)
+ {
+ // Keep polling, but allow other threads to do something useful first
+ ScheduleYield();
+ }
if (testDeviceLost())
{
mDisplay->notifyDeviceLost();
- return gl::Error(GL_OUT_OF_MEMORY, "Device was lost while waiting for sync.");
+ return gl::OutOfMemory() << "Device was lost while waiting for sync.";
}
- }
- while (result == S_FALSE);
+ } while (result == S_FALSE);
- return gl::Error(GL_NO_ERROR);
-}
-
-SwapChainD3D *Renderer11::createSwapChain(NativeWindow nativeWindow,
- HANDLE shareHandle,
- GLenum backBufferFormat,
- GLenum depthBufferFormat,
- EGLint orientation)
-{
- return new SwapChain11(this, nativeWindow, shareHandle, backBufferFormat, depthBufferFormat,
- orientation);
+ return gl::NoError();
}
-CompilerImpl *Renderer11::createCompiler()
+bool Renderer11::isValidNativeWindow(EGLNativeWindowType window) const
{
- if (mRenderer11DeviceCaps.featureLevel <= D3D_FEATURE_LEVEL_9_3)
- {
- return new CompilerD3D(SH_HLSL_4_0_FL9_3_OUTPUT);
- }
- else
- {
- return new CompilerD3D(SH_HLSL_4_1_OUTPUT);
- }
+#ifdef ANGLE_ENABLE_WINDOWS_STORE
+ return NativeWindow11WinRT::IsValidNativeWindow(window);
+#else
+ return NativeWindow11Win32::IsValidNativeWindow(window);
+#endif
}
-void *Renderer11::getD3DDevice()
+NativeWindowD3D *Renderer11::createNativeWindow(EGLNativeWindowType window,
+ const egl::Config *config,
+ const egl::AttributeMap &attribs) const
{
- return reinterpret_cast<void*>(mDevice);
+#ifdef ANGLE_ENABLE_WINDOWS_STORE
+ UNUSED_VARIABLE(attribs);
+ return new NativeWindow11WinRT(window, config->alphaSize > 0);
+#else
+ return new NativeWindow11Win32(
+ window, config->alphaSize > 0,
+ attribs.get(EGL_DIRECT_COMPOSITION_ANGLE, EGL_FALSE) == EGL_TRUE);
+#endif
}
-gl::Error Renderer11::generateSwizzle(gl::Texture *texture)
+egl::Error Renderer11::getD3DTextureInfo(const egl::Config *configuration,
+ IUnknown *d3dTexture,
+ EGLint *width,
+ EGLint *height,
+ GLenum *fboFormat) const
{
- if (texture)
+ ID3D11Texture2D *texture = d3d11::DynamicCastComObject<ID3D11Texture2D>(d3dTexture);
+ if (texture == nullptr)
{
- TextureD3D *textureD3D = GetImplAs<TextureD3D>(texture);
- ASSERT(textureD3D);
-
- TextureStorage *texStorage = nullptr;
- gl::Error error = textureD3D->getNativeTexture(&texStorage);
- if (error.isError())
- {
- return error;
- }
-
- if (texStorage)
- {
- TextureStorage11 *storage11 = GetAs<TextureStorage11>(texStorage);
- const gl::TextureState &textureState = texture->getTextureState();
- error =
- storage11->generateSwizzles(textureState.swizzleRed, textureState.swizzleGreen,
- textureState.swizzleBlue, textureState.swizzleAlpha);
- if (error.isError())
- {
- return error;
- }
- }
+ return egl::EglBadParameter() << "client buffer is not a ID3D11Texture2D";
}
- return gl::Error(GL_NO_ERROR);
-}
-
-gl::Error Renderer11::setSamplerState(gl::SamplerType type,
- int index,
- gl::Texture *texture,
- const gl::SamplerState &samplerState)
-{
- // Make sure to add the level offset for our tiny compressed texture workaround
- TextureD3D *textureD3D = GetImplAs<TextureD3D>(texture);
-
- TextureStorage *storage = nullptr;
- gl::Error error = textureD3D->getNativeTexture(&storage);
- if (error.isError())
+ ID3D11Device *textureDevice = nullptr;
+ texture->GetDevice(&textureDevice);
+ if (textureDevice != mDevice)
{
- return error;
+ SafeRelease(texture);
+ return egl::EglBadParameter() << "Texture's device does not match.";
}
+ SafeRelease(textureDevice);
- // Storage should exist, texture should be complete
- ASSERT(storage);
+ D3D11_TEXTURE2D_DESC desc = {0};
+ texture->GetDesc(&desc);
+ SafeRelease(texture);
- if (type == gl::SAMPLER_PIXEL)
+ if (width)
{
- ASSERT(static_cast<unsigned int>(index) < getRendererCaps().maxTextureImageUnits);
-
- if (mForceSetPixelSamplerStates[index] ||
- memcmp(&samplerState, &mCurPixelSamplerStates[index], sizeof(gl::SamplerState)) != 0)
- {
- ID3D11SamplerState *dxSamplerState = NULL;
- error = mStateCache.getSamplerState(samplerState, &dxSamplerState);
- if (error.isError())
- {
- return error;
- }
-
- ASSERT(dxSamplerState != NULL);
- mDeviceContext->PSSetSamplers(index, 1, &dxSamplerState);
-
- mCurPixelSamplerStates[index] = samplerState;
- }
-
- mForceSetPixelSamplerStates[index] = false;
+ *width = static_cast<EGLint>(desc.Width);
}
- else if (type == gl::SAMPLER_VERTEX)
+ if (height)
{
- ASSERT(static_cast<unsigned int>(index) < getRendererCaps().maxVertexTextureImageUnits);
-
- if (mForceSetVertexSamplerStates[index] ||
- memcmp(&samplerState, &mCurVertexSamplerStates[index], sizeof(gl::SamplerState)) != 0)
- {
- ID3D11SamplerState *dxSamplerState = NULL;
- error = mStateCache.getSamplerState(samplerState, &dxSamplerState);
- if (error.isError())
- {
- return error;
- }
-
- ASSERT(dxSamplerState != NULL);
- mDeviceContext->VSSetSamplers(index, 1, &dxSamplerState);
-
- mCurVertexSamplerStates[index] = samplerState;
- }
-
- mForceSetVertexSamplerStates[index] = false;
+ *height = static_cast<EGLint>(desc.Height);
}
- else UNREACHABLE();
-
- return gl::Error(GL_NO_ERROR);
-}
-
-gl::Error Renderer11::setTexture(gl::SamplerType type, int index, gl::Texture *texture)
-{
- ID3D11ShaderResourceView *textureSRV = NULL;
-
- if (texture)
+ if (static_cast<EGLint>(desc.SampleDesc.Count) != configuration->samples)
{
- TextureD3D *textureImpl = GetImplAs<TextureD3D>(texture);
-
- TextureStorage *texStorage = nullptr;
- gl::Error error = textureImpl->getNativeTexture(&texStorage);
- if (error.isError())
- {
- return error;
- }
-
- // Texture should be complete and have a storage
- ASSERT(texStorage);
-
- TextureStorage11 *storage11 = GetAs<TextureStorage11>(texStorage);
-
- // Make sure to add the level offset for our tiny compressed texture workaround
- gl::TextureState textureState = texture->getTextureState();
- textureState.baseLevel += storage11->getTopLevel();
-
- error = storage11->getSRV(textureState, &textureSRV);
- if (error.isError())
+ // Both the texture and EGL config sample count may not be the same when multi-sampling
+ // is disabled. The EGL sample count can be 0 but a D3D texture is always 1. Therefore,
+ // we must only check for a invalid match when the EGL config is non-zero or the texture is
+ // not one.
+ if (configuration->samples != 0 || desc.SampleDesc.Count != 1)
{
- return error;
+ return egl::EglBadParameter() << "Texture's sample count does not match.";
}
-
- // If we get NULL back from getSRV here, something went wrong in the texture class and we're unexpectedly
- // missing the shader resource view
- ASSERT(textureSRV != NULL);
-
- textureImpl->resetDirty();
}
-
- ASSERT((type == gl::SAMPLER_PIXEL && static_cast<unsigned int>(index) < getRendererCaps().maxTextureImageUnits) ||
- (type == gl::SAMPLER_VERTEX && static_cast<unsigned int>(index) < getRendererCaps().maxVertexTextureImageUnits));
-
- mStateManager.setShaderResource(type, index, textureSRV);
-
- return gl::Error(GL_NO_ERROR);
-}
-
-gl::Error Renderer11::setUniformBuffers(const gl::Data &data,
- const std::vector<GLint> &vertexUniformBuffers,
- const std::vector<GLint> &fragmentUniformBuffers)
-{
- for (size_t uniformBufferIndex = 0; uniformBufferIndex < vertexUniformBuffers.size(); uniformBufferIndex++)
+ // From table egl.restrictions in EGL_ANGLE_d3d_texture_client_buffer.
+ switch (desc.Format)
{
- GLint binding = vertexUniformBuffers[uniformBufferIndex];
-
- if (binding == -1)
- {
- continue;
- }
-
- const OffsetBindingPointer<gl::Buffer> &uniformBuffer =
- data.state->getIndexedUniformBuffer(binding);
- GLintptr uniformBufferOffset = uniformBuffer.getOffset();
- GLsizeiptr uniformBufferSize = uniformBuffer.getSize();
-
- if (uniformBuffer.get() != nullptr)
- {
- Buffer11 *bufferStorage = GetImplAs<Buffer11>(uniformBuffer.get());
- ID3D11Buffer *constantBuffer;
-
- if (mRenderer11DeviceCaps.supportsConstantBufferOffsets)
- {
- constantBuffer = bufferStorage->getBuffer(BUFFER_USAGE_UNIFORM);
- }
- else
- {
- constantBuffer = bufferStorage->getConstantBufferRange(uniformBufferOffset, uniformBufferSize);
- }
-
- if (!constantBuffer)
- {
- return gl::Error(GL_OUT_OF_MEMORY);
- }
-
- if (mCurrentConstantBufferVS[uniformBufferIndex] != bufferStorage->getSerial() ||
- mCurrentConstantBufferVSOffset[uniformBufferIndex] != uniformBufferOffset ||
- mCurrentConstantBufferVSSize[uniformBufferIndex] != uniformBufferSize)
- {
-#if defined(ANGLE_ENABLE_D3D11_1)
- if (mRenderer11DeviceCaps.supportsConstantBufferOffsets && uniformBufferSize != 0)
- {
- UINT firstConstant = 0, numConstants = 0;
- CalculateConstantBufferParams(uniformBufferOffset, uniformBufferSize, &firstConstant, &numConstants);
- mDeviceContext1->VSSetConstantBuffers1(
- getReservedVertexUniformBuffers() +
- static_cast<unsigned int>(uniformBufferIndex),
- 1, &constantBuffer, &firstConstant, &numConstants);
- }
- else
-#endif
- {
- mDeviceContext->VSSetConstantBuffers(
- getReservedVertexUniformBuffers() +
- static_cast<unsigned int>(uniformBufferIndex),
- 1, &constantBuffer);
- }
+ case DXGI_FORMAT_R8G8B8A8_UNORM:
+ case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB:
+ case DXGI_FORMAT_B8G8R8A8_UNORM:
+ case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB:
+ case DXGI_FORMAT_R16G16B16A16_FLOAT:
+ case DXGI_FORMAT_R32G32B32A32_FLOAT:
+ break;
- mCurrentConstantBufferVS[uniformBufferIndex] = bufferStorage->getSerial();
- mCurrentConstantBufferVSOffset[uniformBufferIndex] = uniformBufferOffset;
- mCurrentConstantBufferVSSize[uniformBufferIndex] = uniformBufferSize;
- }
- }
+ default:
+ return egl::EglBadParameter()
+ << "Unknown client buffer texture format: " << desc.Format;
}
- for (size_t uniformBufferIndex = 0; uniformBufferIndex < fragmentUniformBuffers.size(); uniformBufferIndex++)
+ if (fboFormat)
{
- GLint binding = fragmentUniformBuffers[uniformBufferIndex];
-
- if (binding == -1)
- {
- continue;
- }
-
- const OffsetBindingPointer<gl::Buffer> &uniformBuffer =
- data.state->getIndexedUniformBuffer(binding);
- GLintptr uniformBufferOffset = uniformBuffer.getOffset();
- GLsizeiptr uniformBufferSize = uniformBuffer.getSize();
-
- if (uniformBuffer.get() != nullptr)
- {
- Buffer11 *bufferStorage = GetImplAs<Buffer11>(uniformBuffer.get());
- ID3D11Buffer *constantBuffer;
-
- if (mRenderer11DeviceCaps.supportsConstantBufferOffsets)
- {
- constantBuffer = bufferStorage->getBuffer(BUFFER_USAGE_UNIFORM);
- }
- else
- {
- constantBuffer = bufferStorage->getConstantBufferRange(uniformBufferOffset, uniformBufferSize);
- }
-
- if (!constantBuffer)
- {
- return gl::Error(GL_OUT_OF_MEMORY);
- }
-
- if (mCurrentConstantBufferPS[uniformBufferIndex] != bufferStorage->getSerial() ||
- mCurrentConstantBufferPSOffset[uniformBufferIndex] != uniformBufferOffset ||
- mCurrentConstantBufferPSSize[uniformBufferIndex] != uniformBufferSize)
- {
-#if defined(ANGLE_ENABLE_D3D11_1)
- if (mRenderer11DeviceCaps.supportsConstantBufferOffsets && uniformBufferSize != 0)
- {
- UINT firstConstant = 0, numConstants = 0;
- CalculateConstantBufferParams(uniformBufferOffset, uniformBufferSize, &firstConstant, &numConstants);
- mDeviceContext1->PSSetConstantBuffers1(
- getReservedFragmentUniformBuffers() +
- static_cast<unsigned int>(uniformBufferIndex),
- 1, &constantBuffer, &firstConstant, &numConstants);
- }
- else
-#endif
- {
- mDeviceContext->PSSetConstantBuffers(
- getReservedFragmentUniformBuffers() +
- static_cast<unsigned int>(uniformBufferIndex),
- 1, &constantBuffer);
- }
-
- mCurrentConstantBufferPS[uniformBufferIndex] = bufferStorage->getSerial();
- mCurrentConstantBufferPSOffset[uniformBufferIndex] = uniformBufferOffset;
- mCurrentConstantBufferPSSize[uniformBufferIndex] = uniformBufferSize;
- }
- }
+ const angle::Format &angleFormat = d3d11_angle::GetFormat(desc.Format);
+ *fboFormat = angleFormat.fboImplementationInternalFormat;
}
- return gl::Error(GL_NO_ERROR);
+ return egl::NoError();
}
-gl::Error Renderer11::updateState(const gl::Data &data, GLenum drawMode)
+egl::Error Renderer11::validateShareHandle(const egl::Config *config,
+ HANDLE shareHandle,
+ const egl::AttributeMap &attribs) const
{
- // Applies the render target surface, depth stencil surface, viewport rectangle and
- // scissor rectangle to the renderer
- const gl::Framebuffer *framebufferObject = data.state->getDrawFramebuffer();
- ASSERT(framebufferObject && framebufferObject->checkStatus(data) == GL_FRAMEBUFFER_COMPLETE);
- gl::Error error = applyRenderTarget(framebufferObject);
- if (error.isError())
+ if (shareHandle == nullptr)
{
- return error;
+ return egl::EglBadParameter() << "NULL share handle.";
}
- // Set the present path state
- const bool presentPathFastActive =
- UsePresentPathFast(this, framebufferObject->getFirstColorbuffer());
- mStateManager.updatePresentPath(presentPathFastActive,
- framebufferObject->getFirstColorbuffer());
-
- // Setting viewport state
- mStateManager.setViewport(data.caps, data.state->getViewport(), data.state->getNearPlane(),
- data.state->getFarPlane());
-
- // Setting scissor state
- mStateManager.setScissorRectangle(data.state->getScissor(), data.state->isScissorTestEnabled());
-
- // Applying rasterizer state to D3D11 device
- int samples = framebufferObject->getSamples(data);
- gl::RasterizerState rasterizer = data.state->getRasterizerState();
- rasterizer.pointDrawMode = (drawMode == GL_POINTS);
- rasterizer.multiSample = (samples != 0);
-
- error = mStateManager.setRasterizerState(rasterizer);
- if (error.isError())
+ ID3D11Resource *tempResource11 = nullptr;
+ HRESULT result = mDevice->OpenSharedResource(shareHandle, __uuidof(ID3D11Resource),
+ (void **)&tempResource11);
+ if (FAILED(result))
{
- return error;
+ return egl::EglBadParameter() << "Failed to open share handle, " << gl::FmtHR(result);
}
- // Setting blend state
- unsigned int mask = GetBlendSampleMask(data, samples);
- error = mStateManager.setBlendState(framebufferObject, data.state->getBlendState(),
- data.state->getBlendColor(), mask);
- if (error.isError())
+ ID3D11Texture2D *texture2D = d3d11::DynamicCastComObject<ID3D11Texture2D>(tempResource11);
+ SafeRelease(tempResource11);
+
+ if (texture2D == nullptr)
{
- return error;
+ return egl::EglBadParameter()
+ << "Failed to query ID3D11Texture2D object from share handle.";
}
- // Setting depth stencil state
- error = mStateManager.setDepthStencilState(*data.state);
- return error;
-}
-
-void Renderer11::syncState(const gl::State &state, const gl::State::DirtyBits &bitmask)
-{
- mStateManager.syncState(state, bitmask);
-}
-
-bool Renderer11::applyPrimitiveType(GLenum mode, GLsizei count, bool usesPointSize)
-{
- D3D11_PRIMITIVE_TOPOLOGY primitiveTopology = D3D_PRIMITIVE_TOPOLOGY_UNDEFINED;
+ D3D11_TEXTURE2D_DESC desc = {0};
+ texture2D->GetDesc(&desc);
+ SafeRelease(texture2D);
- GLsizei minCount = 0;
+ EGLint width = attribs.getAsInt(EGL_WIDTH, 0);
+ EGLint height = attribs.getAsInt(EGL_HEIGHT, 0);
+ ASSERT(width != 0 && height != 0);
- switch (mode)
- {
- case GL_POINTS: primitiveTopology = D3D11_PRIMITIVE_TOPOLOGY_POINTLIST; minCount = 1; break;
- case GL_LINES: primitiveTopology = D3D_PRIMITIVE_TOPOLOGY_LINELIST; minCount = 2; break;
- case GL_LINE_LOOP: primitiveTopology = D3D_PRIMITIVE_TOPOLOGY_LINESTRIP; minCount = 2; break;
- case GL_LINE_STRIP: primitiveTopology = D3D_PRIMITIVE_TOPOLOGY_LINESTRIP; minCount = 2; break;
- case GL_TRIANGLES: primitiveTopology = D3D_PRIMITIVE_TOPOLOGY_TRIANGLELIST; minCount = 3; break;
- case GL_TRIANGLE_STRIP: primitiveTopology = D3D_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP; minCount = 3; break;
- // emulate fans via rewriting index buffer
- case GL_TRIANGLE_FAN: primitiveTopology = D3D_PRIMITIVE_TOPOLOGY_TRIANGLELIST; minCount = 3; break;
- default:
- UNREACHABLE();
- return false;
- }
+ const d3d11::Format &backbufferFormatInfo =
+ d3d11::Format::Get(config->renderTargetFormat, getRenderer11DeviceCaps());
- // If instanced pointsprite emulation is being used and If gl_PointSize is used in the shader,
- // GL_POINTS mode is expected to render pointsprites.
- // Instanced PointSprite emulation requires that the topology to be D3D_PRIMITIVE_TOPOLOGY_TRIANGLELIST.
- if (mode == GL_POINTS && usesPointSize && getWorkarounds().useInstancedPointSpriteEmulation)
+ if (desc.Width != static_cast<UINT>(width) || desc.Height != static_cast<UINT>(height) ||
+ desc.Format != backbufferFormatInfo.texFormat || desc.MipLevels != 1 || desc.ArraySize != 1)
{
- primitiveTopology = D3D_PRIMITIVE_TOPOLOGY_TRIANGLELIST;
+ return egl::EglBadParameter() << "Invalid texture parameters in share handle texture.";
}
- if (primitiveTopology != mCurrentPrimitiveTopology)
- {
- mDeviceContext->IASetPrimitiveTopology(primitiveTopology);
- mCurrentPrimitiveTopology = primitiveTopology;
- }
-
- return count >= minCount;
+ return egl::NoError();
}
-gl::Error Renderer11::applyRenderTarget(const gl::Framebuffer *framebuffer)
+SwapChainD3D *Renderer11::createSwapChain(NativeWindowD3D *nativeWindow,
+ HANDLE shareHandle,
+ IUnknown *d3dTexture,
+ GLenum backBufferFormat,
+ GLenum depthBufferFormat,
+ EGLint orientation,
+ EGLint samples)
{
- return mStateManager.syncFramebuffer(framebuffer);
+ return new SwapChain11(this, GetAs<NativeWindow11>(nativeWindow), shareHandle, d3dTexture,
+ backBufferFormat, depthBufferFormat, orientation, samples);
}
-gl::Error Renderer11::applyVertexBuffer(const gl::State &state,
- GLenum mode,
- GLint first,
- GLsizei count,
- GLsizei instances,
- TranslatedIndexData *indexInfo)
+void *Renderer11::getD3DDevice()
{
- gl::Error error = mVertexDataManager->prepareVertexData(state, first, count, &mTranslatedAttribCache, instances);
- if (error.isError())
- {
- return error;
- }
-
- // If index information is passed, mark it with the current changed status.
- if (indexInfo)
- {
- indexInfo->srcIndexData.srcIndicesChanged = mAppliedIBChanged;
- }
-
- GLsizei numIndicesPerInstance = 0;
- if (instances > 0)
- {
- numIndicesPerInstance = count;
- }
- return mInputLayoutCache.applyVertexBuffers(mTranslatedAttribCache, mode, state.getProgram(),
- indexInfo, numIndicesPerInstance);
+ return reinterpret_cast<void *>(mDevice);
}
-gl::Error Renderer11::applyIndexBuffer(const gl::Data &data,
- const GLvoid *indices,
- GLsizei count,
- GLenum mode,
- GLenum type,
- TranslatedIndexData *indexInfo)
+bool Renderer11::applyPrimitiveType(const gl::State &glState, GLenum mode, GLsizei count)
{
- gl::VertexArray *vao = data.state->getVertexArray();
- gl::Buffer *elementArrayBuffer = vao->getElementArrayBuffer().get();
- gl::Error error =
- mIndexDataManager->prepareIndexData(type, count, elementArrayBuffer, indices, indexInfo,
- data.state->isPrimitiveRestartEnabled());
- if (error.isError())
- {
- return error;
- }
-
- ID3D11Buffer *buffer = NULL;
- DXGI_FORMAT bufferFormat = (indexInfo->indexType == GL_UNSIGNED_INT) ? DXGI_FORMAT_R32_UINT : DXGI_FORMAT_R16_UINT;
-
- if (indexInfo->storage)
- {
- Buffer11 *storage = GetAs<Buffer11>(indexInfo->storage);
- buffer = storage->getBuffer(BUFFER_USAGE_INDEX);
- }
- else
- {
- IndexBuffer11* indexBuffer = GetAs<IndexBuffer11>(indexInfo->indexBuffer);
- buffer = indexBuffer->getBuffer();
- }
-
- mAppliedIBChanged = false;
- if (buffer != mAppliedIB || bufferFormat != mAppliedIBFormat || indexInfo->startOffset != mAppliedIBOffset)
- {
- mDeviceContext->IASetIndexBuffer(buffer, bufferFormat, indexInfo->startOffset);
-
- mAppliedIB = buffer;
- mAppliedIBFormat = bufferFormat;
- mAppliedIBOffset = indexInfo->startOffset;
- mAppliedIBChanged = true;
- }
-
- return gl::Error(GL_NO_ERROR);
-}
+ D3D11_PRIMITIVE_TOPOLOGY primitiveTopology = D3D_PRIMITIVE_TOPOLOGY_UNDEFINED;
-void Renderer11::applyTransformFeedbackBuffers(const gl::State &state)
-{
- size_t numXFBBindings = 0;
- bool requiresUpdate = false;
+ GLsizei minCount = 0;
- if (state.isTransformFeedbackActiveUnpaused())
+ switch (mode)
{
- const gl::TransformFeedback *transformFeedback = state.getCurrentTransformFeedback();
- numXFBBindings = transformFeedback->getIndexedBufferCount();
- ASSERT(numXFBBindings <= gl::IMPLEMENTATION_MAX_TRANSFORM_FEEDBACK_BUFFERS);
-
- for (size_t i = 0; i < numXFBBindings; i++)
+ case GL_POINTS:
{
- const OffsetBindingPointer<gl::Buffer> &binding = transformFeedback->getIndexedBuffer(i);
-
- ID3D11Buffer *d3dBuffer = NULL;
- if (binding.get() != nullptr)
- {
- Buffer11 *storage = GetImplAs<Buffer11>(binding.get());
- d3dBuffer = storage->getBuffer(BUFFER_USAGE_VERTEX_OR_TRANSFORM_FEEDBACK);
- }
+ bool usesPointSize = GetImplAs<ProgramD3D>(glState.getProgram())->usesPointSize();
- // TODO: mAppliedTFBuffers and friends should also be kept in a vector.
- if (d3dBuffer != mAppliedTFBuffers[i] || binding.getOffset() != mAppliedTFOffsets[i])
+ // ProgramBinary assumes non-point rendering if gl_PointSize isn't written,
+ // which affects varying interpolation. Since the value of gl_PointSize is
+ // undefined when not written, just skip drawing to avoid unexpected results.
+ if (!usesPointSize && !glState.isTransformFeedbackActiveUnpaused())
{
- requiresUpdate = true;
+ // Notify developers of risking undefined behavior.
+ WARN() << "Point rendering without writing to gl_PointSize.";
+ return false;
}
- }
- }
- if (requiresUpdate || numXFBBindings != mAppliedNumXFBBindings)
- {
- const gl::TransformFeedback *transformFeedback = state.getCurrentTransformFeedback();
- for (size_t i = 0; i < numXFBBindings; ++i)
- {
- const OffsetBindingPointer<gl::Buffer> &binding = transformFeedback->getIndexedBuffer(i);
- if (binding.get() != nullptr)
+ // If instanced pointsprites are enabled and the shader uses gl_PointSize, the topology
+ // must be D3D_PRIMITIVE_TOPOLOGY_TRIANGLELIST.
+ if (usesPointSize && getWorkarounds().useInstancedPointSpriteEmulation)
{
- Buffer11 *storage = GetImplAs<Buffer11>(binding.get());
- ID3D11Buffer *d3dBuffer = storage->getBuffer(BUFFER_USAGE_VERTEX_OR_TRANSFORM_FEEDBACK);
-
- mCurrentD3DOffsets[i] = (mAppliedTFBuffers[i] != d3dBuffer || mAppliedTFOffsets[i] != binding.getOffset()) ?
- static_cast<UINT>(binding.getOffset()) : -1;
- mAppliedTFBuffers[i] = d3dBuffer;
+ primitiveTopology = D3D_PRIMITIVE_TOPOLOGY_TRIANGLELIST;
}
else
{
- mAppliedTFBuffers[i] = NULL;
- mCurrentD3DOffsets[i] = 0;
+ primitiveTopology = D3D11_PRIMITIVE_TOPOLOGY_POINTLIST;
}
- mAppliedTFOffsets[i] = binding.getOffset();
+ minCount = 1;
+ break;
}
+ case GL_LINES:
+ primitiveTopology = D3D_PRIMITIVE_TOPOLOGY_LINELIST;
+ minCount = 2;
+ break;
+ case GL_LINE_LOOP:
+ primitiveTopology = D3D_PRIMITIVE_TOPOLOGY_LINESTRIP;
+ minCount = 2;
+ break;
+ case GL_LINE_STRIP:
+ primitiveTopology = D3D_PRIMITIVE_TOPOLOGY_LINESTRIP;
+ minCount = 2;
+ break;
+ case GL_TRIANGLES:
+ primitiveTopology = D3D_PRIMITIVE_TOPOLOGY_TRIANGLELIST;
+ minCount = CullsEverything(glState) ? std::numeric_limits<GLsizei>::max() : 3;
+ break;
+ case GL_TRIANGLE_STRIP:
+ primitiveTopology = D3D_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP;
+ minCount = CullsEverything(glState) ? std::numeric_limits<GLsizei>::max() : 3;
+ break;
+ // emulate fans via rewriting index buffer
+ case GL_TRIANGLE_FAN:
+ primitiveTopology = D3D_PRIMITIVE_TOPOLOGY_TRIANGLELIST;
+ minCount = CullsEverything(glState) ? std::numeric_limits<GLsizei>::max() : 3;
+ break;
+ default:
+ UNREACHABLE();
+ return false;
+ }
- mAppliedNumXFBBindings = numXFBBindings;
+ mStateManager.setPrimitiveTopology(primitiveTopology);
- mDeviceContext->SOSetTargets(static_cast<unsigned int>(numXFBBindings), mAppliedTFBuffers,
- mCurrentD3DOffsets);
- }
+ return count >= minCount;
}
-gl::Error Renderer11::drawArraysImpl(const gl::Data &data,
- GLenum mode,
- GLsizei count,
- GLsizei instances)
+gl::Error Renderer11::drawArrays(const gl::Context *context,
+ GLenum mode,
+ GLint startVertex,
+ GLsizei count,
+ GLsizei instances)
{
- ProgramD3D *programD3D = GetImplAs<ProgramD3D>(data.state->getProgram());
+ const auto &glState = context->getGLState();
- if (programD3D->usesGeometryShader(mode) && data.state->isTransformFeedbackActiveUnpaused())
+ if (!applyPrimitiveType(glState, mode, count))
+ {
+ return gl::NoError();
+ }
+
+ DrawCallVertexParams vertexParams(startVertex, count, instances);
+ ANGLE_TRY(mStateManager.applyVertexBuffer(context, mode, vertexParams, false));
+
+ if (glState.isTransformFeedbackActiveUnpaused())
+ {
+ ANGLE_TRY(markTransformFeedbackUsage(context));
+ }
+
+ gl::Program *program = glState.getProgram();
+ ASSERT(program != nullptr);
+ GLsizei adjustedInstanceCount = GetAdjustedInstanceCount(program, instances);
+ ProgramD3D *programD3D = GetImplAs<ProgramD3D>(program);
+
+ if (programD3D->usesGeometryShader(mode) && glState.isTransformFeedbackActiveUnpaused())
{
// Since we use a geometry if-and-only-if we rewrite vertex streams, transform feedback
// won't get the correct output. To work around this, draw with *only* the stream out
// first (no pixel shader) to feed the stream out buffers and then draw again with the
// geometry shader + pixel shader to rasterize the primitives.
- mDeviceContext->PSSetShader(nullptr, nullptr, 0);
+ mStateManager.setPixelShader(nullptr);
- if (instances > 0)
+ if (adjustedInstanceCount > 0)
{
- mDeviceContext->DrawInstanced(count, instances, 0, 0);
+ mDeviceContext->DrawInstanced(count, adjustedInstanceCount, 0, 0);
}
else
{
@@ -1673,203 +1561,330 @@ gl::Error Renderer11::drawArraysImpl(const gl::Data &data,
}
rx::ShaderExecutableD3D *pixelExe = nullptr;
- gl::Error error = programD3D->getPixelExecutableForFramebuffer(data.state->getDrawFramebuffer(), &pixelExe);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(programD3D->getPixelExecutableForCachedOutputLayout(&pixelExe, nullptr));
// Skip the draw call if rasterizer discard is enabled (or no fragment shader).
- if (!pixelExe || data.state->getRasterizerState().rasterizerDiscard)
+ if (!pixelExe || glState.getRasterizerState().rasterizerDiscard)
{
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
- ID3D11PixelShader *pixelShader = GetAs<ShaderExecutable11>(pixelExe)->getPixelShader();
- ASSERT(reinterpret_cast<uintptr_t>(pixelShader) == mAppliedPixelShader);
- mDeviceContext->PSSetShader(pixelShader, NULL, 0);
+ mStateManager.setPixelShader(&GetAs<ShaderExecutable11>(pixelExe)->getPixelShader());
// Retrieve the geometry shader.
rx::ShaderExecutableD3D *geometryExe = nullptr;
- error =
- programD3D->getGeometryExecutableForPrimitiveType(data, mode, &geometryExe, nullptr);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(programD3D->getGeometryExecutableForPrimitiveType(context, mode, &geometryExe,
+ nullptr));
- ID3D11GeometryShader *geometryShader =
- (geometryExe ? GetAs<ShaderExecutable11>(geometryExe)->getGeometryShader() : NULL);
- mAppliedGeometryShader = reinterpret_cast<uintptr_t>(geometryShader);
- ASSERT(geometryShader);
- mDeviceContext->GSSetShader(geometryShader, NULL, 0);
+ mStateManager.setGeometryShader(
+ &GetAs<ShaderExecutable11>(geometryExe)->getGeometryShader());
- if (instances > 0)
+ if (adjustedInstanceCount > 0)
{
- mDeviceContext->DrawInstanced(count, instances, 0, 0);
+ mDeviceContext->DrawInstanced(count, adjustedInstanceCount, 0, 0);
}
else
{
mDeviceContext->Draw(count, 0);
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
if (mode == GL_LINE_LOOP)
{
- return drawLineLoop(data, count, GL_NONE, nullptr, nullptr, instances);
+ return drawLineLoop(context, count, GL_NONE, nullptr, 0, adjustedInstanceCount);
}
if (mode == GL_TRIANGLE_FAN)
{
- return drawTriangleFan(data, count, GL_NONE, nullptr, 0, instances);
+ return drawTriangleFan(context, count, GL_NONE, nullptr, 0, adjustedInstanceCount);
}
bool useInstancedPointSpriteEmulation =
programD3D->usesPointSize() && getWorkarounds().useInstancedPointSpriteEmulation;
- if (instances > 0)
+ if (mode != GL_POINTS || !useInstancedPointSpriteEmulation)
{
- if (mode == GL_POINTS && useInstancedPointSpriteEmulation)
+ if (adjustedInstanceCount == 0)
{
- // If pointsprite emulation is used with glDrawArraysInstanced then we need to take a
- // less efficent code path.
- // Instanced rendering of emulated pointsprites requires a loop to draw each batch of
- // points. An offset into the instanced data buffer is calculated and applied on each
- // iteration to ensure all instances are rendered correctly.
-
- // Each instance being rendered requires the inputlayout cache to reapply buffers and
- // offsets.
- for (GLsizei i = 0; i < instances; i++)
- {
- gl::Error error = mInputLayoutCache.updateVertexOffsetsForPointSpritesEmulation(i);
- if (error.isError())
- {
- return error;
- }
-
- mDeviceContext->DrawIndexedInstanced(6, count, 0, 0, 0);
- }
+ mDeviceContext->Draw(count, 0);
}
else
{
- mDeviceContext->DrawInstanced(count, instances, 0, 0);
+ mDeviceContext->DrawInstanced(count, adjustedInstanceCount, 0, 0);
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
+ // This code should not be reachable by multi-view programs.
+ ASSERT(program->usesMultiview() == false);
+
// If the shader is writing to gl_PointSize, then pointsprites are being rendered.
// Emulating instanced point sprites for FL9_3 requires the topology to be
// D3D_PRIMITIVE_TOPOLOGY_TRIANGLELIST and DrawIndexedInstanced is called instead.
- if (mode == GL_POINTS && useInstancedPointSpriteEmulation)
+ if (adjustedInstanceCount == 0)
{
mDeviceContext->DrawIndexedInstanced(6, count, 0, 0, 0);
+ return gl::NoError();
}
- else
+
+ // If pointsprite emulation is used with glDrawArraysInstanced then we need to take a less
+ // efficent code path. Instanced rendering of emulated pointsprites requires a loop to draw each
+ // batch of points. An offset into the instanced data buffer is calculated and applied on each
+ // iteration to ensure all instances are rendered correctly. Each instance being rendered
+ // requires the inputlayout cache to reapply buffers and offsets.
+ for (GLsizei i = 0; i < instances; i++)
{
- mDeviceContext->Draw(count, 0);
+ ANGLE_TRY(mStateManager.updateVertexOffsetsForPointSpritesEmulation(startVertex, i));
+ mDeviceContext->DrawIndexedInstanced(6, count, 0, 0, 0);
}
- return gl::Error(GL_NO_ERROR);
+
+ // This required by updateVertexOffsets... above but is outside of the loop for speed.
+ mStateManager.invalidateVertexBuffer();
+ return gl::NoError();
}
-gl::Error Renderer11::drawElementsImpl(const gl::Data &data,
- const TranslatedIndexData &indexInfo,
- GLenum mode,
- GLsizei count,
- GLenum type,
- const GLvoid *indices,
- GLsizei instances)
+gl::Error Renderer11::drawElements(const gl::Context *context,
+ GLenum mode,
+ GLsizei count,
+ GLenum type,
+ const void *indices,
+ GLsizei instances)
{
- int minIndex = static_cast<int>(indexInfo.indexRange.start);
+ const auto &glState = context->getGLState();
+
+ if (!applyPrimitiveType(glState, mode, count))
+ {
+ return gl::NoError();
+ }
+
+ // Transform feedback is not allowed for DrawElements, this error should have been caught at the
+ // API validation layer.
+ ASSERT(!glState.isTransformFeedbackActiveUnpaused());
+
+ const auto &lazyIndexRange = context->getParams<gl::HasIndexRange>();
+
+ bool usePrimitiveRestartWorkaround =
+ UsePrimitiveRestartWorkaround(glState.isPrimitiveRestartEnabled(), type);
+ DrawCallVertexParams vertexParams(!usePrimitiveRestartWorkaround, lazyIndexRange, 0, instances);
+
+ ANGLE_TRY(mStateManager.applyIndexBuffer(context, indices, count, type, lazyIndexRange,
+ usePrimitiveRestartWorkaround));
+ ANGLE_TRY(mStateManager.applyVertexBuffer(context, mode, vertexParams, true));
+
+ int startVertex = static_cast<int>(vertexParams.firstVertex());
+ int baseVertex = -startVertex;
+
+ const gl::Program *program = glState.getProgram();
+ GLsizei adjustedInstanceCount = GetAdjustedInstanceCount(program, instances);
if (mode == GL_LINE_LOOP)
{
- return drawLineLoop(data, count, type, indices, &indexInfo, instances);
+ return drawLineLoop(context, count, type, indices, baseVertex, adjustedInstanceCount);
}
if (mode == GL_TRIANGLE_FAN)
{
- return drawTriangleFan(data, count, type, indices, minIndex, instances);
+ return drawTriangleFan(context, count, type, indices, baseVertex, adjustedInstanceCount);
}
- const ProgramD3D *programD3D = GetImplAs<ProgramD3D>(data.state->getProgram());
- if (instances > 0)
+ const ProgramD3D *programD3D = GetImplAs<ProgramD3D>(glState.getProgram());
+
+ if (mode != GL_POINTS || !programD3D->usesInstancedPointSpriteEmulation())
{
- if (mode == GL_POINTS && programD3D->usesInstancedPointSpriteEmulation())
+ if (adjustedInstanceCount == 0)
{
- // If pointsprite emulation is used with glDrawElementsInstanced then we need to take a
- // less efficent code path.
- // Instanced rendering of emulated pointsprites requires a loop to draw each batch of
- // points. An offset into the instanced data buffer is calculated and applied on each
- // iteration to ensure all instances are rendered correctly.
- GLsizei elementsToRender = static_cast<GLsizei>(indexInfo.indexRange.vertexCount());
-
- // Each instance being rendered requires the inputlayout cache to reapply buffers and
- // offsets.
- for (GLsizei i = 0; i < instances; i++)
- {
- gl::Error error = mInputLayoutCache.updateVertexOffsetsForPointSpritesEmulation(i);
- if (error.isError())
- {
- return error;
- }
-
- mDeviceContext->DrawIndexedInstanced(6, elementsToRender, 0, 0, 0);
- }
+ mDeviceContext->DrawIndexed(count, 0, baseVertex);
}
else
{
- mDeviceContext->DrawIndexedInstanced(count, instances, 0, -minIndex, 0);
+ mDeviceContext->DrawIndexedInstanced(count, adjustedInstanceCount, 0, baseVertex, 0);
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
+ // This code should not be reachable by multi-view programs.
+ ASSERT(program->usesMultiview() == false);
+
// If the shader is writing to gl_PointSize, then pointsprites are being rendered.
// Emulating instanced point sprites for FL9_3 requires the topology to be
// D3D_PRIMITIVE_TOPOLOGY_TRIANGLELIST and DrawIndexedInstanced is called instead.
- if (mode == GL_POINTS && programD3D->usesInstancedPointSpriteEmulation())
- {
- // The count parameter passed to drawElements represents the total number of instances
- // to be rendered. Each instance is referenced by the bound index buffer from the
- // the caller.
- //
- // Indexed pointsprite emulation replicates data for duplicate entries found
- // in the index buffer.
- // This is not an efficent rendering mechanism and is only used on downlevel renderers
- // that do not support geometry shaders.
+ //
+ // The count parameter passed to drawElements represents the total number of instances to be
+ // rendered. Each instance is referenced by the bound index buffer from the the caller.
+ //
+ // Indexed pointsprite emulation replicates data for duplicate entries found in the index
+ // buffer. This is not an efficent rendering mechanism and is only used on downlevel renderers
+ // that do not support geometry shaders.
+ if (instances == 0)
+ {
mDeviceContext->DrawIndexedInstanced(6, count, 0, 0, 0);
+ return gl::NoError();
}
- else
+
+ // If pointsprite emulation is used with glDrawElementsInstanced then we need to take a less
+ // efficent code path. Instanced rendering of emulated pointsprites requires a loop to draw each
+ // batch of points. An offset into the instanced data buffer is calculated and applied on each
+ // iteration to ensure all instances are rendered correctly.
+ GLsizei elementsToRender = vertexParams.vertexCount();
+
+ // Each instance being rendered requires the inputlayout cache to reapply buffers and offsets.
+ for (GLsizei i = 0; i < instances; i++)
+ {
+ ANGLE_TRY(mStateManager.updateVertexOffsetsForPointSpritesEmulation(startVertex, i));
+ mDeviceContext->DrawIndexedInstanced(6, elementsToRender, 0, 0, 0);
+ }
+ mStateManager.invalidateVertexBuffer();
+ return gl::NoError();
+}
+
+gl::Error Renderer11::drawArraysIndirect(const gl::Context *context,
+ GLenum mode,
+ const void *indirect)
+{
+ const auto &glState = context->getGLState();
+ ASSERT(!glState.isTransformFeedbackActiveUnpaused());
+
+ if (!applyPrimitiveType(glState, mode, std::numeric_limits<int>::max() - 1))
+ {
+ return gl::NoError();
+ }
+
+ gl::Buffer *drawIndirectBuffer = glState.getTargetBuffer(gl::BufferBinding::DrawIndirect);
+ ASSERT(drawIndirectBuffer);
+ Buffer11 *storage = GetImplAs<Buffer11>(drawIndirectBuffer);
+ uintptr_t offset = reinterpret_cast<uintptr_t>(indirect);
+
+ if (!DrawCallNeedsTranslation(context, mode))
+ {
+ DrawCallVertexParams vertexParams(0, 0, 0);
+ ANGLE_TRY(mStateManager.applyVertexBuffer(context, mode, vertexParams, false));
+ ID3D11Buffer *buffer = nullptr;
+ ANGLE_TRY_RESULT(storage->getBuffer(context, BUFFER_USAGE_INDIRECT), buffer);
+ mDeviceContext->DrawInstancedIndirect(buffer, static_cast<unsigned int>(offset));
+ return gl::NoError();
+ }
+
+ const uint8_t *bufferData = nullptr;
+ ANGLE_TRY(storage->getData(context, &bufferData));
+ ASSERT(bufferData);
+ const gl::DrawArraysIndirectCommand *args =
+ reinterpret_cast<const gl::DrawArraysIndirectCommand *>(bufferData + offset);
+ GLuint count = args->count;
+ GLuint instances = args->instanceCount;
+ GLuint first = args->first;
+
+ DrawCallVertexParams vertexParams(first, count, instances);
+ ANGLE_TRY(mStateManager.applyVertexBuffer(context, mode, vertexParams, false));
+
+ if (mode == GL_LINE_LOOP)
+ {
+ return drawLineLoop(context, count, GL_NONE, nullptr, 0, instances);
+ }
+ if (mode == GL_TRIANGLE_FAN)
+ {
+ return drawTriangleFan(context, count, GL_NONE, nullptr, 0, instances);
+ }
+
+ mDeviceContext->DrawInstanced(count, instances, 0, 0);
+ return gl::NoError();
+}
+
+gl::Error Renderer11::drawElementsIndirect(const gl::Context *context,
+ GLenum mode,
+ GLenum type,
+ const void *indirect)
+{
+ const auto &glState = context->getGLState();
+ ASSERT(!glState.isTransformFeedbackActiveUnpaused());
+
+ if (!applyPrimitiveType(glState, mode, std::numeric_limits<int>::max() - 1))
+ {
+ return gl::NoError();
+ }
+
+ gl::Buffer *drawIndirectBuffer = glState.getTargetBuffer(gl::BufferBinding::DrawIndirect);
+ ASSERT(drawIndirectBuffer);
+ Buffer11 *storage = GetImplAs<Buffer11>(drawIndirectBuffer);
+ uintptr_t offset = reinterpret_cast<uintptr_t>(indirect);
+
+ // TODO(jmadill): Remove the if statement and compute indirect parameters lazily.
+ bool usePrimitiveRestartWorkaround =
+ UsePrimitiveRestartWorkaround(glState.isPrimitiveRestartEnabled(), type);
+
+ if (!DrawCallNeedsTranslation(context, mode) && !IsStreamingIndexData(context, type))
+ {
+ ANGLE_TRY(mStateManager.applyIndexBuffer(context, nullptr, 0, type, gl::HasIndexRange(),
+ usePrimitiveRestartWorkaround));
+ DrawCallVertexParams vertexParams(0, 0, 0);
+ ANGLE_TRY(mStateManager.applyVertexBuffer(context, mode, vertexParams, true));
+ ID3D11Buffer *buffer = nullptr;
+ ANGLE_TRY_RESULT(storage->getBuffer(context, BUFFER_USAGE_INDIRECT), buffer);
+ mDeviceContext->DrawIndexedInstancedIndirect(buffer, static_cast<unsigned int>(offset));
+ return gl::NoError();
+ }
+
+ const uint8_t *bufferData = nullptr;
+ ANGLE_TRY(storage->getData(context, &bufferData));
+ ASSERT(bufferData);
+
+ const gl::DrawElementsIndirectCommand *cmd =
+ reinterpret_cast<const gl::DrawElementsIndirectCommand *>(bufferData + offset);
+ GLsizei count = cmd->count;
+ GLuint instances = cmd->primCount;
+ GLuint firstIndex = cmd->firstIndex;
+ GLint baseVertex = cmd->baseVertex;
+
+ // TODO(jmadill): Fix const cast.
+ const gl::Type &typeInfo = gl::GetTypeInfo(type);
+ const void *indices =
+ reinterpret_cast<const void *>(static_cast<uintptr_t>(firstIndex * typeInfo.bytes));
+ gl::HasIndexRange lazyIndexRange(const_cast<gl::Context *>(context), count, type, indices);
+
+ ANGLE_TRY(mStateManager.applyIndexBuffer(context, indices, count, type, lazyIndexRange,
+ usePrimitiveRestartWorkaround));
+
+ DrawCallVertexParams vertexParams(false, lazyIndexRange, baseVertex, instances);
+
+ ANGLE_TRY(mStateManager.applyVertexBuffer(context, mode, vertexParams, true));
+
+ int baseVertexLocation = -static_cast<int>(lazyIndexRange.getIndexRange().value().start);
+
+ if (mode == GL_LINE_LOOP)
{
- mDeviceContext->DrawIndexed(count, 0, -minIndex);
+ return drawLineLoop(context, count, type, indices, baseVertexLocation, instances);
}
- return gl::Error(GL_NO_ERROR);
+
+ if (mode == GL_TRIANGLE_FAN)
+ {
+ return drawTriangleFan(context, count, type, indices, baseVertexLocation, instances);
+ }
+
+ mDeviceContext->DrawIndexedInstanced(count, instances, 0, baseVertexLocation, 0);
+ return gl::NoError();
}
-gl::Error Renderer11::drawLineLoop(const gl::Data &data,
+gl::Error Renderer11::drawLineLoop(const gl::Context *context,
GLsizei count,
GLenum type,
- const GLvoid *indexPointer,
- const TranslatedIndexData *indexInfo,
+ const void *indexPointer,
+ int baseVertex,
int instances)
{
- gl::VertexArray *vao = data.state->getVertexArray();
+ const gl::State &glState = context->getGLState();
+ gl::VertexArray *vao = glState.getVertexArray();
gl::Buffer *elementArrayBuffer = vao->getElementArrayBuffer().get();
- const GLvoid *indices = indexPointer;
+ const void *indices = indexPointer;
// Get the raw indices for an indexed draw
if (type != GL_NONE && elementArrayBuffer)
{
BufferD3D *storage = GetImplAs<BufferD3D>(elementArrayBuffer);
- intptr_t offset = reinterpret_cast<intptr_t>(indices);
+ intptr_t offset = reinterpret_cast<intptr_t>(indices);
- const uint8_t *bufferData = NULL;
- gl::Error error = storage->getData(&bufferData);
- if (error.isError())
- {
- return error;
- }
+ const uint8_t *bufferData = nullptr;
+ ANGLE_TRY(storage->getData(context, &bufferData));
indices = bufferData + offset;
}
@@ -1877,7 +1892,8 @@ gl::Error Renderer11::drawLineLoop(const gl::Data &data,
if (!mLineLoopIB)
{
mLineLoopIB = new StreamingIndexBufferInterface(this);
- gl::Error error = mLineLoopIB->reserveBufferSpace(INITIAL_INDEX_BUFFER_SIZE, GL_UNSIGNED_INT);
+ gl::Error error =
+ mLineLoopIB->reserveBufferSpace(INITIAL_INDEX_BUFFER_SIZE, GL_UNSIGNED_INT);
if (error.isError())
{
SafeDelete(mLineLoopIB);
@@ -1888,92 +1904,71 @@ gl::Error Renderer11::drawLineLoop(const gl::Data &data,
// Checked by Renderer11::applyPrimitiveType
ASSERT(count >= 0);
- if (static_cast<unsigned int>(count) + 1 > (std::numeric_limits<unsigned int>::max() / sizeof(unsigned int)))
+ if (static_cast<unsigned int>(count) + 1 >
+ (std::numeric_limits<unsigned int>::max() / sizeof(unsigned int)))
{
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create a 32-bit looping index buffer for GL_LINE_LOOP, too many indices required.");
+ return gl::OutOfMemory() << "Failed to create a 32-bit looping index buffer for "
+ "GL_LINE_LOOP, too many indices required.";
}
GetLineLoopIndices(indices, type, static_cast<GLuint>(count),
- data.state->isPrimitiveRestartEnabled(), &mScratchIndexDataBuffer);
+ glState.isPrimitiveRestartEnabled(), &mScratchIndexDataBuffer);
unsigned int spaceNeeded =
static_cast<unsigned int>(sizeof(GLuint) * mScratchIndexDataBuffer.size());
- gl::Error error = mLineLoopIB->reserveBufferSpace(spaceNeeded, GL_UNSIGNED_INT);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(mLineLoopIB->reserveBufferSpace(spaceNeeded, GL_UNSIGNED_INT));
- void* mappedMemory = NULL;
+ void *mappedMemory = nullptr;
unsigned int offset;
- error = mLineLoopIB->mapBuffer(spaceNeeded, &mappedMemory, &offset);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(mLineLoopIB->mapBuffer(spaceNeeded, &mappedMemory, &offset));
// Copy over the converted index data.
memcpy(mappedMemory, &mScratchIndexDataBuffer[0],
sizeof(GLuint) * mScratchIndexDataBuffer.size());
- error = mLineLoopIB->unmapBuffer();
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(mLineLoopIB->unmapBuffer());
- IndexBuffer11 *indexBuffer = GetAs<IndexBuffer11>(mLineLoopIB->getIndexBuffer());
- ID3D11Buffer *d3dIndexBuffer = indexBuffer->getBuffer();
- DXGI_FORMAT indexFormat = indexBuffer->getIndexFormat();
+ IndexBuffer11 *indexBuffer = GetAs<IndexBuffer11>(mLineLoopIB->getIndexBuffer());
+ const d3d11::Buffer &d3dIndexBuffer = indexBuffer->getBuffer();
+ DXGI_FORMAT indexFormat = indexBuffer->getIndexFormat();
- if (mAppliedIB != d3dIndexBuffer || mAppliedIBFormat != indexFormat ||
- mAppliedIBOffset != offset)
- {
- mDeviceContext->IASetIndexBuffer(d3dIndexBuffer, indexFormat, offset);
- mAppliedIB = d3dIndexBuffer;
- mAppliedIBFormat = indexFormat;
- mAppliedIBOffset = offset;
- }
+ mStateManager.setIndexBuffer(d3dIndexBuffer.get(), indexFormat, offset);
- INT baseVertexLocation = (indexInfo ? -static_cast<int>(indexInfo->indexRange.start) : 0);
UINT indexCount = static_cast<UINT>(mScratchIndexDataBuffer.size());
if (instances > 0)
{
- mDeviceContext->DrawIndexedInstanced(indexCount, instances, 0, baseVertexLocation, 0);
+ mDeviceContext->DrawIndexedInstanced(indexCount, instances, 0, baseVertex, 0);
}
else
{
- mDeviceContext->DrawIndexed(indexCount, 0, baseVertexLocation);
+ mDeviceContext->DrawIndexed(indexCount, 0, baseVertex);
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error Renderer11::drawTriangleFan(const gl::Data &data,
+gl::Error Renderer11::drawTriangleFan(const gl::Context *context,
GLsizei count,
GLenum type,
- const GLvoid *indices,
- int minIndex,
+ const void *indices,
+ int baseVertex,
int instances)
{
- gl::VertexArray *vao = data.state->getVertexArray();
+ const gl::State &glState = context->getGLState();
+ gl::VertexArray *vao = glState.getVertexArray();
gl::Buffer *elementArrayBuffer = vao->getElementArrayBuffer().get();
- const GLvoid *indexPointer = indices;
+ const void *indexPointer = indices;
// Get the raw indices for an indexed draw
if (type != GL_NONE && elementArrayBuffer)
{
BufferD3D *storage = GetImplAs<BufferD3D>(elementArrayBuffer);
- intptr_t offset = reinterpret_cast<intptr_t>(indices);
+ intptr_t offset = reinterpret_cast<intptr_t>(indices);
- const uint8_t *bufferData = NULL;
- gl::Error error = storage->getData(&bufferData);
- if (error.isError())
- {
- return error;
- }
+ const uint8_t *bufferData = nullptr;
+ ANGLE_TRY(storage->getData(context, &bufferData));
indexPointer = bufferData + offset;
}
@@ -1981,7 +1976,8 @@ gl::Error Renderer11::drawTriangleFan(const gl::Data &data,
if (!mTriangleFanIB)
{
mTriangleFanIB = new StreamingIndexBufferInterface(this);
- gl::Error error = mTriangleFanIB->reserveBufferSpace(INITIAL_INDEX_BUFFER_SIZE, GL_UNSIGNED_INT);
+ gl::Error error =
+ mTriangleFanIB->reserveBufferSpace(INITIAL_INDEX_BUFFER_SIZE, GL_UNSIGNED_INT);
if (error.isError())
{
SafeDelete(mTriangleFanIB);
@@ -1996,386 +1992,50 @@ gl::Error Renderer11::drawTriangleFan(const gl::Data &data,
if (numTris > (std::numeric_limits<unsigned int>::max() / (sizeof(unsigned int) * 3)))
{
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create a scratch index buffer for GL_TRIANGLE_FAN, too many indices required.");
+ return gl::OutOfMemory() << "Failed to create a scratch index buffer for GL_TRIANGLE_FAN, "
+ "too many indices required.";
}
- GetTriFanIndices(indexPointer, type, count, data.state->isPrimitiveRestartEnabled(),
+ GetTriFanIndices(indexPointer, type, count, glState.isPrimitiveRestartEnabled(),
&mScratchIndexDataBuffer);
const unsigned int spaceNeeded =
static_cast<unsigned int>(mScratchIndexDataBuffer.size() * sizeof(unsigned int));
- gl::Error error = mTriangleFanIB->reserveBufferSpace(spaceNeeded, GL_UNSIGNED_INT);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(mTriangleFanIB->reserveBufferSpace(spaceNeeded, GL_UNSIGNED_INT));
void *mappedMemory = nullptr;
unsigned int offset;
- error = mTriangleFanIB->mapBuffer(spaceNeeded, &mappedMemory, &offset);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(mTriangleFanIB->mapBuffer(spaceNeeded, &mappedMemory, &offset));
memcpy(mappedMemory, &mScratchIndexDataBuffer[0], spaceNeeded);
- error = mTriangleFanIB->unmapBuffer();
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(mTriangleFanIB->unmapBuffer());
- IndexBuffer11 *indexBuffer = GetAs<IndexBuffer11>(mTriangleFanIB->getIndexBuffer());
- ID3D11Buffer *d3dIndexBuffer = indexBuffer->getBuffer();
- DXGI_FORMAT indexFormat = indexBuffer->getIndexFormat();
+ IndexBuffer11 *indexBuffer = GetAs<IndexBuffer11>(mTriangleFanIB->getIndexBuffer());
+ const d3d11::Buffer &d3dIndexBuffer = indexBuffer->getBuffer();
+ DXGI_FORMAT indexFormat = indexBuffer->getIndexFormat();
- if (mAppliedIB != d3dIndexBuffer || mAppliedIBFormat != indexFormat ||
- mAppliedIBOffset != offset)
- {
- mDeviceContext->IASetIndexBuffer(d3dIndexBuffer, indexFormat, offset);
- mAppliedIB = d3dIndexBuffer;
- mAppliedIBFormat = indexFormat;
- mAppliedIBOffset = offset;
- }
+ mStateManager.setIndexBuffer(d3dIndexBuffer.get(), indexFormat, offset);
UINT indexCount = static_cast<UINT>(mScratchIndexDataBuffer.size());
if (instances > 0)
{
- mDeviceContext->DrawIndexedInstanced(indexCount, instances, 0, -minIndex, 0);
+ mDeviceContext->DrawIndexedInstanced(indexCount, instances, 0, baseVertex, 0);
}
else
{
- mDeviceContext->DrawIndexed(indexCount, 0, -minIndex);
+ mDeviceContext->DrawIndexed(indexCount, 0, baseVertex);
}
- return gl::Error(GL_NO_ERROR);
-}
-
-gl::Error Renderer11::applyShadersImpl(const gl::Data &data, GLenum drawMode)
-{
- ProgramD3D *programD3D = GetImplAs<ProgramD3D>(data.state->getProgram());
- const auto &inputLayout = programD3D->getCachedInputLayout();
-
- ShaderExecutableD3D *vertexExe = NULL;
- gl::Error error = programD3D->getVertexExecutableForInputLayout(inputLayout, &vertexExe, nullptr);
- if (error.isError())
- {
- return error;
- }
-
- const gl::Framebuffer *drawFramebuffer = data.state->getDrawFramebuffer();
- ShaderExecutableD3D *pixelExe = NULL;
- error = programD3D->getPixelExecutableForFramebuffer(drawFramebuffer, &pixelExe);
- if (error.isError())
- {
- return error;
- }
-
- ShaderExecutableD3D *geometryExe = nullptr;
- error =
- programD3D->getGeometryExecutableForPrimitiveType(data, drawMode, &geometryExe, nullptr);
- if (error.isError())
- {
- return error;
- }
-
- ID3D11VertexShader *vertexShader = (vertexExe ? GetAs<ShaderExecutable11>(vertexExe)->getVertexShader() : NULL);
-
- ID3D11PixelShader *pixelShader = NULL;
- // Skip pixel shader if we're doing rasterizer discard.
- bool rasterizerDiscard = data.state->getRasterizerState().rasterizerDiscard;
- if (!rasterizerDiscard)
- {
- pixelShader = (pixelExe ? GetAs<ShaderExecutable11>(pixelExe)->getPixelShader() : NULL);
- }
-
- ID3D11GeometryShader *geometryShader = NULL;
- bool transformFeedbackActive = data.state->isTransformFeedbackActiveUnpaused();
- if (transformFeedbackActive)
- {
- geometryShader = (vertexExe ? GetAs<ShaderExecutable11>(vertexExe)->getStreamOutShader() : NULL);
- }
- else
- {
- geometryShader = (geometryExe ? GetAs<ShaderExecutable11>(geometryExe)->getGeometryShader() : NULL);
- }
-
- bool dirtyUniforms = false;
-
- if (reinterpret_cast<uintptr_t>(vertexShader) != mAppliedVertexShader)
- {
- mDeviceContext->VSSetShader(vertexShader, NULL, 0);
- mAppliedVertexShader = reinterpret_cast<uintptr_t>(vertexShader);
- dirtyUniforms = true;
- }
-
- if (reinterpret_cast<uintptr_t>(geometryShader) != mAppliedGeometryShader)
- {
- mDeviceContext->GSSetShader(geometryShader, NULL, 0);
- mAppliedGeometryShader = reinterpret_cast<uintptr_t>(geometryShader);
- dirtyUniforms = true;
- }
-
- if (reinterpret_cast<uintptr_t>(pixelShader) != mAppliedPixelShader)
- {
- mDeviceContext->PSSetShader(pixelShader, NULL, 0);
- mAppliedPixelShader = reinterpret_cast<uintptr_t>(pixelShader);
- dirtyUniforms = true;
- }
-
- if (dirtyUniforms)
- {
- programD3D->dirtyAllUniforms();
- }
-
- return gl::Error(GL_NO_ERROR);
-}
-
-gl::Error Renderer11::applyUniforms(const ProgramD3D &programD3D,
- GLenum drawMode,
- const std::vector<D3DUniform *> &uniformArray)
-{
- unsigned int totalRegisterCountVS = 0;
- unsigned int totalRegisterCountPS = 0;
-
- bool vertexUniformsDirty = false;
- bool pixelUniformsDirty = false;
-
- for (const D3DUniform *uniform : uniformArray)
- {
- if (uniform->isReferencedByVertexShader() && !uniform->isSampler())
- {
- totalRegisterCountVS += uniform->registerCount;
- vertexUniformsDirty = (vertexUniformsDirty || uniform->dirty);
- }
-
- if (uniform->isReferencedByFragmentShader() && !uniform->isSampler())
- {
- totalRegisterCountPS += uniform->registerCount;
- pixelUniformsDirty = (pixelUniformsDirty || uniform->dirty);
- }
- }
-
- const UniformStorage11 *vertexUniformStorage =
- GetAs<UniformStorage11>(&programD3D.getVertexUniformStorage());
- const UniformStorage11 *fragmentUniformStorage =
- GetAs<UniformStorage11>(&programD3D.getFragmentUniformStorage());
- ASSERT(vertexUniformStorage);
- ASSERT(fragmentUniformStorage);
-
- ID3D11Buffer *vertexConstantBuffer = vertexUniformStorage->getConstantBuffer();
- ID3D11Buffer *pixelConstantBuffer = fragmentUniformStorage->getConstantBuffer();
-
- float (*mapVS)[4] = NULL;
- float (*mapPS)[4] = NULL;
-
- if (totalRegisterCountVS > 0 && vertexUniformsDirty)
- {
- D3D11_MAPPED_SUBRESOURCE map = {0};
- HRESULT result = mDeviceContext->Map(vertexConstantBuffer, 0, D3D11_MAP_WRITE_DISCARD, 0, &map);
- UNUSED_ASSERTION_VARIABLE(result);
- ASSERT(SUCCEEDED(result));
- mapVS = (float(*)[4])map.pData;
- }
-
- if (totalRegisterCountPS > 0 && pixelUniformsDirty)
- {
- D3D11_MAPPED_SUBRESOURCE map = {0};
- HRESULT result = mDeviceContext->Map(pixelConstantBuffer, 0, D3D11_MAP_WRITE_DISCARD, 0, &map);
- UNUSED_ASSERTION_VARIABLE(result);
- ASSERT(SUCCEEDED(result));
- mapPS = (float(*)[4])map.pData;
- }
-
- for (const D3DUniform *uniform : uniformArray)
- {
- if (uniform->isSampler())
- continue;
-
- unsigned int componentCount = (4 - uniform->registerElement);
-
- // we assume that uniforms from structs are arranged in struct order in our uniforms list.
- // otherwise we would overwrite previously written regions of memory.
-
- if (uniform->isReferencedByVertexShader() && mapVS)
- {
- memcpy(&mapVS[uniform->vsRegisterIndex][uniform->registerElement], uniform->data,
- uniform->registerCount * sizeof(float) * componentCount);
- }
-
- if (uniform->isReferencedByFragmentShader() && mapPS)
- {
- memcpy(&mapPS[uniform->psRegisterIndex][uniform->registerElement], uniform->data,
- uniform->registerCount * sizeof(float) * componentCount);
- }
- }
-
- if (mapVS)
- {
- mDeviceContext->Unmap(vertexConstantBuffer, 0);
- }
-
- if (mapPS)
- {
- mDeviceContext->Unmap(pixelConstantBuffer, 0);
- }
-
- if (mCurrentVertexConstantBuffer != vertexConstantBuffer)
- {
- mDeviceContext->VSSetConstantBuffers(0, 1, &vertexConstantBuffer);
- mCurrentVertexConstantBuffer = vertexConstantBuffer;
- }
-
- if (mCurrentPixelConstantBuffer != pixelConstantBuffer)
- {
- mDeviceContext->PSSetConstantBuffers(0, 1, &pixelConstantBuffer);
- mCurrentPixelConstantBuffer = pixelConstantBuffer;
- }
-
- // Driver uniforms
- if (!mDriverConstantBufferVS)
- {
- D3D11_BUFFER_DESC constantBufferDescription = {0};
- constantBufferDescription.ByteWidth = sizeof(dx_VertexConstants11);
- constantBufferDescription.Usage = D3D11_USAGE_DEFAULT;
- constantBufferDescription.BindFlags = D3D11_BIND_CONSTANT_BUFFER;
- constantBufferDescription.CPUAccessFlags = 0;
- constantBufferDescription.MiscFlags = 0;
- constantBufferDescription.StructureByteStride = 0;
-
- HRESULT result = mDevice->CreateBuffer(&constantBufferDescription, NULL, &mDriverConstantBufferVS);
- ASSERT(SUCCEEDED(result));
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create vertex shader constant buffer, result: 0x%X.", result);
- }
- mDeviceContext->VSSetConstantBuffers(1, 1, &mDriverConstantBufferVS);
- }
-
- if (!mDriverConstantBufferPS)
- {
- D3D11_BUFFER_DESC constantBufferDescription = {0};
- constantBufferDescription.ByteWidth = sizeof(dx_PixelConstants11);
- constantBufferDescription.Usage = D3D11_USAGE_DEFAULT;
- constantBufferDescription.BindFlags = D3D11_BIND_CONSTANT_BUFFER;
- constantBufferDescription.CPUAccessFlags = 0;
- constantBufferDescription.MiscFlags = 0;
- constantBufferDescription.StructureByteStride = 0;
-
- HRESULT result = mDevice->CreateBuffer(&constantBufferDescription, NULL, &mDriverConstantBufferPS);
- ASSERT(SUCCEEDED(result));
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create pixel shader constant buffer, result: 0x%X.", result);
- }
- mDeviceContext->PSSetConstantBuffers(1, 1, &mDriverConstantBufferPS);
- }
-
- const dx_VertexConstants11 &vertexConstants = mStateManager.getVertexConstants();
- if (memcmp(&vertexConstants, &mAppliedVertexConstants, sizeof(dx_VertexConstants11)) != 0)
- {
- ASSERT(mDriverConstantBufferVS != nullptr);
- if (mDriverConstantBufferVS)
- {
- mDeviceContext->UpdateSubresource(mDriverConstantBufferVS, 0, NULL, &vertexConstants,
- 16, 0);
- memcpy(&mAppliedVertexConstants, &vertexConstants, sizeof(dx_VertexConstants11));
- }
- }
-
- const dx_PixelConstants11 &pixelConstants = mStateManager.getPixelConstants();
- if (memcmp(&pixelConstants, &mAppliedPixelConstants, sizeof(dx_PixelConstants11)) != 0)
- {
- ASSERT(mDriverConstantBufferPS != nullptr);
- if (mDriverConstantBufferPS)
- {
- mDeviceContext->UpdateSubresource(mDriverConstantBufferPS, 0, NULL, &pixelConstants, 16,
- 0);
- memcpy(&mAppliedPixelConstants, &pixelConstants, sizeof(dx_PixelConstants11));
- }
- }
-
- // GSSetConstantBuffers triggers device removal on 9_3, so we should only call it if necessary
- if (programD3D.usesGeometryShader(drawMode))
- {
- // needed for the point sprite geometry shader
- if (mCurrentGeometryConstantBuffer != mDriverConstantBufferPS)
- {
- ASSERT(mDriverConstantBufferPS != nullptr);
- if (mDriverConstantBufferPS)
- {
- mDeviceContext->GSSetConstantBuffers(0, 1, &mDriverConstantBufferPS);
- mCurrentGeometryConstantBuffer = mDriverConstantBufferPS;
- }
- }
- }
-
- return gl::Error(GL_NO_ERROR);
-}
-
-void Renderer11::markAllStateDirty()
-{
- TRACE_EVENT0("gpu.angle", "Renderer11::markAllStateDirty");
-
- for (size_t vsamplerId = 0; vsamplerId < mForceSetVertexSamplerStates.size(); ++vsamplerId)
- {
- mForceSetVertexSamplerStates[vsamplerId] = true;
- }
-
- for (size_t fsamplerId = 0; fsamplerId < mForceSetPixelSamplerStates.size(); ++fsamplerId)
- {
- mForceSetPixelSamplerStates[fsamplerId] = true;
- }
-
- mStateManager.invalidateEverything();
-
- mAppliedIB = NULL;
- mAppliedIBFormat = DXGI_FORMAT_UNKNOWN;
- mAppliedIBOffset = 0;
-
- mAppliedVertexShader = angle::DirtyPointer;
- mAppliedGeometryShader = angle::DirtyPointer;
- mAppliedPixelShader = angle::DirtyPointer;
-
- mAppliedNumXFBBindings = static_cast<size_t>(-1);
-
- for (size_t i = 0; i < gl::IMPLEMENTATION_MAX_TRANSFORM_FEEDBACK_BUFFERS; i++)
- {
- mAppliedTFBuffers[i] = NULL;
- mAppliedTFOffsets[i] = 0;
- }
-
- memset(&mAppliedVertexConstants, 0, sizeof(dx_VertexConstants11));
- memset(&mAppliedPixelConstants, 0, sizeof(dx_PixelConstants11));
-
- mInputLayoutCache.markDirty();
-
- for (unsigned int i = 0; i < gl::IMPLEMENTATION_MAX_VERTEX_SHADER_UNIFORM_BUFFERS; i++)
- {
- mCurrentConstantBufferVS[i] = static_cast<unsigned int>(-1);
- mCurrentConstantBufferVSOffset[i] = 0;
- mCurrentConstantBufferVSSize[i] = 0;
- mCurrentConstantBufferPS[i] = static_cast<unsigned int>(-1);
- mCurrentConstantBufferPSOffset[i] = 0;
- mCurrentConstantBufferPSSize[i] = 0;
- }
-
- mCurrentVertexConstantBuffer = NULL;
- mCurrentPixelConstantBuffer = NULL;
- mCurrentGeometryConstantBuffer = NULL;
-
- mCurrentPrimitiveTopology = D3D_PRIMITIVE_TOPOLOGY_UNDEFINED;
+ return gl::NoError();
}
void Renderer11::releaseDeviceResources()
{
+ mStateManager.deinitialize();
mStateCache.clear();
- mInputLayoutCache.clear();
- SafeDelete(mVertexDataManager);
- SafeDelete(mIndexDataManager);
SafeDelete(mLineLoopIB);
SafeDelete(mTriangleFanIB);
SafeDelete(mBlit);
@@ -2383,9 +2043,9 @@ void Renderer11::releaseDeviceResources()
SafeDelete(mTrim);
SafeDelete(mPixelTransfer);
- SafeRelease(mDriverConstantBufferVS);
- SafeRelease(mDriverConstantBufferPS);
- SafeRelease(mSyncQuery);
+ mSyncQuery.reset();
+
+ mCachedResolveTexture.reset();
}
// set notify to true to broadcast a message to all contexts of the device loss
@@ -2393,24 +2053,18 @@ bool Renderer11::testDeviceLost()
{
bool isLost = false;
+ if (!mDevice)
+ {
+ return true;
+ }
+
// GetRemovedReason is used to test if the device is removed
HRESULT result = mDevice->GetDeviceRemovedReason();
- isLost = d3d11::isDeviceLostError(result);
+ isLost = d3d11::isDeviceLostError(result);
if (isLost)
{
- // Log error if this is a new device lost event
- if (mDeviceLost == false)
- {
- ERR("The D3D11 device was removed: 0x%08X", result);
- }
-
- // ensure we note the device loss --
- // we'll probably get this done again by notifyDeviceLost
- // but best to remember it!
- // Note that we don't want to clear the device loss status here
- // -- this needs to be done by resetDevice
- mDeviceLost = true;
+ ERR() << "The D3D11 device was removed, " << gl::FmtHR(result);
}
return isLost;
@@ -2419,27 +2073,24 @@ bool Renderer11::testDeviceLost()
bool Renderer11::testDeviceResettable()
{
// determine if the device is resettable by creating a dummy device
- PFN_D3D11_CREATE_DEVICE D3D11CreateDevice = (PFN_D3D11_CREATE_DEVICE)GetProcAddress(mD3d11Module, "D3D11CreateDevice");
+ PFN_D3D11_CREATE_DEVICE D3D11CreateDevice =
+ (PFN_D3D11_CREATE_DEVICE)GetProcAddress(mD3d11Module, "D3D11CreateDevice");
- if (D3D11CreateDevice == NULL)
+ if (D3D11CreateDevice == nullptr)
{
return false;
}
- ID3D11Device* dummyDevice;
+ ID3D11Device *dummyDevice;
D3D_FEATURE_LEVEL dummyFeatureLevel;
- ID3D11DeviceContext* dummyContext;
+ ID3D11DeviceContext *dummyContext;
+ UINT flags = (mCreateDebugDevice ? D3D11_CREATE_DEVICE_DEBUG : 0);
ASSERT(mRequestedDriverType != D3D_DRIVER_TYPE_UNKNOWN);
HRESULT result = D3D11CreateDevice(
- NULL, mRequestedDriverType, NULL,
- #if defined(_DEBUG)
- D3D11_CREATE_DEVICE_DEBUG,
- #else
- 0,
- #endif
- mAvailableFeatureLevels.data(), static_cast<unsigned int>(mAvailableFeatureLevels.size()),
- D3D11_SDK_VERSION, &dummyDevice, &dummyFeatureLevel, &dummyContext);
+ nullptr, mRequestedDriverType, nullptr, flags, mAvailableFeatureLevels.data(),
+ static_cast<unsigned int>(mAvailableFeatureLevels.size()), D3D11_SDK_VERSION, &dummyDevice,
+ &dummyFeatureLevel, &dummyContext);
if (!mDevice || FAILED(result))
{
@@ -2456,6 +2107,14 @@ void Renderer11::release()
{
RendererD3D::cleanup();
+ mScratchMemoryBuffer.clear();
+
+ if (mAnnotator != nullptr)
+ {
+ gl::UninitializeDebugAnnotations();
+ SafeDelete(mAnnotator);
+ }
+
releaseDeviceResources();
if (!mCreatedWithDeviceEXT)
@@ -2468,9 +2127,8 @@ void Renderer11::release()
SafeRelease(mDxgiFactory);
SafeRelease(mDxgiAdapter);
-#if defined(ANGLE_ENABLE_D3D11_1)
+ SafeRelease(mDeviceContext3);
SafeRelease(mDeviceContext1);
-#endif
if (mDeviceContext)
{
@@ -2480,26 +2138,24 @@ void Renderer11::release()
}
SafeRelease(mDevice);
-#if !defined(ANGLE_MINGW32_COMPAT)
SafeRelease(mDebug);
-#endif
if (mD3d11Module)
{
FreeLibrary(mD3d11Module);
- mD3d11Module = NULL;
+ mD3d11Module = nullptr;
}
if (mDxgiModule)
{
FreeLibrary(mDxgiModule);
- mDxgiModule = NULL;
+ mDxgiModule = nullptr;
}
if (mDCompModule)
{
FreeLibrary(mDCompModule);
- mDCompModule = NULL;
+ mDCompModule = nullptr;
}
mCompiler.release();
@@ -2515,12 +2171,10 @@ bool Renderer11::resetDevice()
if (result.isError())
{
- ERR("Could not reinitialize D3D11 device: %08X", result.getCode());
+ ERR() << "Could not reinitialize D3D11 device: " << result;
return false;
}
- mDeviceLost = false;
-
return true;
}
@@ -2531,8 +2185,10 @@ std::string Renderer11::getRendererDescription() const
rendererString << mDescription;
rendererString << " Direct3D11";
- rendererString << " vs_" << getMajorShaderModel() << "_" << getMinorShaderModel() << getShaderModelSuffix();
- rendererString << " ps_" << getMajorShaderModel() << "_" << getMinorShaderModel() << getShaderModelSuffix();
+ rendererString << " vs_" << getMajorShaderModel() << "_" << getMinorShaderModel()
+ << getShaderModelSuffix();
+ rendererString << " ps_" << getMajorShaderModel() << "_" << getMinorShaderModel()
+ << getShaderModelSuffix();
return rendererString.str();
}
@@ -2540,12 +2196,12 @@ std::string Renderer11::getRendererDescription() const
DeviceIdentifier Renderer11::getAdapterIdentifier() const
{
// Don't use the AdapterLuid here, since that doesn't persist across reboot.
- DeviceIdentifier deviceIdentifier = { 0 };
- deviceIdentifier.VendorId = mAdapterDescription.VendorId;
- deviceIdentifier.DeviceId = mAdapterDescription.DeviceId;
- deviceIdentifier.SubSysId = mAdapterDescription.SubSysId;
- deviceIdentifier.Revision = mAdapterDescription.Revision;
- deviceIdentifier.FeatureLevel = static_cast<UINT>(mRenderer11DeviceCaps.featureLevel);
+ DeviceIdentifier deviceIdentifier = {0};
+ deviceIdentifier.VendorId = mAdapterDescription.VendorId;
+ deviceIdentifier.DeviceId = mAdapterDescription.DeviceId;
+ deviceIdentifier.SubSysId = mAdapterDescription.SubSysId;
+ deviceIdentifier.Revision = mAdapterDescription.Revision;
+ deviceIdentifier.FeatureLevel = static_cast<UINT>(mRenderer11DeviceCaps.featureLevel);
return deviceIdentifier;
}
@@ -2605,7 +2261,7 @@ bool Renderer11::getShareHandleSupport() const
// We only currently support share handles with BGRA surfaces, because
// chrome needs BGRA. Once chrome fixes this, we should always support them.
- if (!getRendererExtensions().textureFormatBGRA8888)
+ if (!getNativeExtensions().textureFormatBGRA8888)
{
mSupportsShareHandles = false;
return false;
@@ -2620,7 +2276,8 @@ bool Renderer11::getShareHandleSupport() const
// Qt: we don't care about the 9_3 limitation
#if 0
- // Also disable share handles on Feature Level 9_3, since it doesn't support share handles on RGBA8 textures/swapchains.
+ // Also disable share handles on Feature Level 9_3, since it doesn't support share handles on
+ // RGBA8 textures/swapchains.
if (mRenderer11DeviceCaps.featureLevel <= D3D_FEATURE_LEVEL_9_3)
{
mSupportsShareHandles = false;
@@ -2668,15 +2325,34 @@ bool Renderer11::getShareHandleSupport() const
return true;
}
+bool Renderer11::getNV12TextureSupport() const
+{
+ HRESULT result;
+ UINT formatSupport;
+ result = mDevice->CheckFormatSupport(DXGI_FORMAT_NV12, &formatSupport);
+ if (result == E_FAIL)
+ {
+ return false;
+ }
+ return (formatSupport & D3D11_FORMAT_SUPPORT_TEXTURE2D) != 0;
+}
+
int Renderer11::getMajorShaderModel() const
{
switch (mRenderer11DeviceCaps.featureLevel)
{
- case D3D_FEATURE_LEVEL_11_0: return D3D11_SHADER_MAJOR_VERSION; // 5
- case D3D_FEATURE_LEVEL_10_1: return D3D10_1_SHADER_MAJOR_VERSION; // 4
- case D3D_FEATURE_LEVEL_10_0: return D3D10_SHADER_MAJOR_VERSION; // 4
- case D3D_FEATURE_LEVEL_9_3: return D3D10_SHADER_MAJOR_VERSION; // 4
- default: UNREACHABLE(); return 0;
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return D3D11_SHADER_MAJOR_VERSION; // 5
+ case D3D_FEATURE_LEVEL_10_1:
+ return D3D10_1_SHADER_MAJOR_VERSION; // 4
+ case D3D_FEATURE_LEVEL_10_0:
+ return D3D10_SHADER_MAJOR_VERSION; // 4
+ case D3D_FEATURE_LEVEL_9_3:
+ return D3D10_SHADER_MAJOR_VERSION; // 4
+ default:
+ UNREACHABLE();
+ return 0;
}
}
@@ -2684,11 +2360,18 @@ int Renderer11::getMinorShaderModel() const
{
switch (mRenderer11DeviceCaps.featureLevel)
{
- case D3D_FEATURE_LEVEL_11_0: return D3D11_SHADER_MINOR_VERSION; // 0
- case D3D_FEATURE_LEVEL_10_1: return D3D10_1_SHADER_MINOR_VERSION; // 1
- case D3D_FEATURE_LEVEL_10_0: return D3D10_SHADER_MINOR_VERSION; // 0
- case D3D_FEATURE_LEVEL_9_3: return D3D10_SHADER_MINOR_VERSION; // 0
- default: UNREACHABLE(); return 0;
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return D3D11_SHADER_MINOR_VERSION; // 0
+ case D3D_FEATURE_LEVEL_10_1:
+ return D3D10_1_SHADER_MINOR_VERSION; // 1
+ case D3D_FEATURE_LEVEL_10_0:
+ return D3D10_SHADER_MINOR_VERSION; // 0
+ case D3D_FEATURE_LEVEL_9_3:
+ return D3D10_SHADER_MINOR_VERSION; // 0
+ default:
+ UNREACHABLE();
+ return 0;
}
}
@@ -2696,15 +2379,22 @@ std::string Renderer11::getShaderModelSuffix() const
{
switch (mRenderer11DeviceCaps.featureLevel)
{
- case D3D_FEATURE_LEVEL_11_0: return "";
- case D3D_FEATURE_LEVEL_10_1: return "";
- case D3D_FEATURE_LEVEL_10_0: return "";
- case D3D_FEATURE_LEVEL_9_3: return "_level_9_3";
- default: UNREACHABLE(); return "";
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return "";
+ case D3D_FEATURE_LEVEL_10_1:
+ return "";
+ case D3D_FEATURE_LEVEL_10_0:
+ return "";
+ case D3D_FEATURE_LEVEL_9_3:
+ return "_level_9_3";
+ default:
+ UNREACHABLE();
+ return "";
}
}
-const WorkaroundsD3D &RendererD3D::getWorkarounds() const
+const angle::WorkaroundsD3D &RendererD3D::getWorkarounds() const
{
if (!mWorkaroundsInitialized)
{
@@ -2715,42 +2405,31 @@ const WorkaroundsD3D &RendererD3D::getWorkarounds() const
return mWorkarounds;
}
-gl::Error Renderer11::copyImage2D(const gl::Framebuffer *framebuffer, const gl::Rectangle &sourceRect, GLenum destFormat,
- const gl::Offset &destOffset, TextureStorage *storage, GLint level)
+gl::Error Renderer11::copyImageInternal(const gl::Context *context,
+ const gl::Framebuffer *framebuffer,
+ const gl::Rectangle &sourceRect,
+ GLenum destFormat,
+ const gl::Offset &destOffset,
+ RenderTargetD3D *destRenderTarget)
{
- const gl::FramebufferAttachment *colorbuffer = framebuffer->getReadColorbuffer();
- ASSERT(colorbuffer);
+ const gl::FramebufferAttachment *colorAttachment = framebuffer->getReadColorbuffer();
+ ASSERT(colorAttachment);
- RenderTarget11 *sourceRenderTarget = NULL;
- gl::Error error = colorbuffer->getRenderTarget(&sourceRenderTarget);
- if (error.isError())
- {
- return error;
- }
+ RenderTarget11 *sourceRenderTarget = nullptr;
+ ANGLE_TRY(colorAttachment->getRenderTarget(context, &sourceRenderTarget));
ASSERT(sourceRenderTarget);
- ID3D11ShaderResourceView *source = sourceRenderTarget->getShaderResourceView();
- ASSERT(source);
-
- TextureStorage11_2D *storage11 = GetAs<TextureStorage11_2D>(storage);
- ASSERT(storage11);
-
- gl::ImageIndex index = gl::ImageIndex::Make2D(level);
- RenderTargetD3D *destRenderTarget = NULL;
- error = storage11->getRenderTarget(index, &destRenderTarget);
- if (error.isError())
- {
- return error;
- }
- ASSERT(destRenderTarget);
+ const d3d11::SharedSRV &source = sourceRenderTarget->getBlitShaderResourceView();
+ ASSERT(source.valid());
- ID3D11RenderTargetView *dest = GetAs<RenderTarget11>(destRenderTarget)->getRenderTargetView();
- ASSERT(dest);
+ const d3d11::RenderTargetView &dest =
+ GetAs<RenderTarget11>(destRenderTarget)->getRenderTargetView();
+ ASSERT(dest.valid());
gl::Box sourceArea(sourceRect.x, sourceRect.y, 0, sourceRect.width, sourceRect.height, 1);
gl::Extents sourceSize(sourceRenderTarget->getWidth(), sourceRenderTarget->getHeight(), 1);
- const bool invertSource = UsePresentPathFast(this, colorbuffer);
+ const bool invertSource = UsePresentPathFast(this, colorAttachment);
if (invertSource)
{
sourceArea.y = sourceSize.height - sourceRect.y;
@@ -2760,226 +2439,267 @@ gl::Error Renderer11::copyImage2D(const gl::Framebuffer *framebuffer, const gl::
gl::Box destArea(destOffset.x, destOffset.y, 0, sourceRect.width, sourceRect.height, 1);
gl::Extents destSize(destRenderTarget->getWidth(), destRenderTarget->getHeight(), 1);
- // Use nearest filtering because source and destination are the same size for the direct
- // copy
- error = mBlit->copyTexture(source, sourceArea, sourceSize, dest, destArea, destSize, NULL,
- destFormat, GL_NEAREST, false);
- if (error.isError())
- {
- return error;
- }
+ // Use nearest filtering because source and destination are the same size for the direct copy.
+ // Convert to the unsized format before calling copyTexture.
+ GLenum sourceFormat = colorAttachment->getFormat().info->format;
+ ANGLE_TRY(mBlit->copyTexture(context, source, sourceArea, sourceSize, sourceFormat, dest,
+ destArea, destSize, nullptr, gl::GetUnsizedFormat(destFormat),
+ GL_NEAREST, false, false, false));
- storage11->invalidateSwizzleCacheLevel(level);
-
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error Renderer11::copyImageCube(const gl::Framebuffer *framebuffer, const gl::Rectangle &sourceRect, GLenum destFormat,
- const gl::Offset &destOffset, TextureStorage *storage, GLenum target, GLint level)
+gl::Error Renderer11::copyImage2D(const gl::Context *context,
+ const gl::Framebuffer *framebuffer,
+ const gl::Rectangle &sourceRect,
+ GLenum destFormat,
+ const gl::Offset &destOffset,
+ TextureStorage *storage,
+ GLint level)
{
- const gl::FramebufferAttachment *colorbuffer = framebuffer->getReadColorbuffer();
- ASSERT(colorbuffer);
+ TextureStorage11_2D *storage11 = GetAs<TextureStorage11_2D>(storage);
+ ASSERT(storage11);
- RenderTarget11 *sourceRenderTarget = NULL;
- gl::Error error = colorbuffer->getRenderTarget(&sourceRenderTarget);
- if (error.isError())
- {
- return error;
- }
- ASSERT(sourceRenderTarget);
+ gl::ImageIndex index = gl::ImageIndex::Make2D(level);
+ RenderTargetD3D *destRenderTarget = nullptr;
+ ANGLE_TRY(storage11->getRenderTarget(context, index, &destRenderTarget));
+ ASSERT(destRenderTarget);
+
+ ANGLE_TRY(copyImageInternal(context, framebuffer, sourceRect, destFormat, destOffset,
+ destRenderTarget));
+
+ storage11->markLevelDirty(level);
- ID3D11ShaderResourceView *source = sourceRenderTarget->getShaderResourceView();
- ASSERT(source);
+ return gl::NoError();
+}
+gl::Error Renderer11::copyImageCube(const gl::Context *context,
+ const gl::Framebuffer *framebuffer,
+ const gl::Rectangle &sourceRect,
+ GLenum destFormat,
+ const gl::Offset &destOffset,
+ TextureStorage *storage,
+ GLenum target,
+ GLint level)
+{
TextureStorage11_Cube *storage11 = GetAs<TextureStorage11_Cube>(storage);
ASSERT(storage11);
- gl::ImageIndex index = gl::ImageIndex::MakeCube(target, level);
- RenderTargetD3D *destRenderTarget = NULL;
- error = storage11->getRenderTarget(index, &destRenderTarget);
- if (error.isError())
- {
- return error;
- }
+ gl::ImageIndex index = gl::ImageIndex::MakeCube(target, level);
+ RenderTargetD3D *destRenderTarget = nullptr;
+ ANGLE_TRY(storage11->getRenderTarget(context, index, &destRenderTarget));
ASSERT(destRenderTarget);
- ID3D11RenderTargetView *dest = GetAs<RenderTarget11>(destRenderTarget)->getRenderTargetView();
- ASSERT(dest);
+ ANGLE_TRY(copyImageInternal(context, framebuffer, sourceRect, destFormat, destOffset,
+ destRenderTarget));
- gl::Box sourceArea(sourceRect.x, sourceRect.y, 0, sourceRect.width, sourceRect.height, 1);
- gl::Extents sourceSize(sourceRenderTarget->getWidth(), sourceRenderTarget->getHeight(), 1);
+ storage11->markLevelDirty(level);
- const bool invertSource = UsePresentPathFast(this, colorbuffer);
- if (invertSource)
- {
- sourceArea.y = sourceSize.height - sourceRect.y;
- sourceArea.height = -sourceArea.height;
- }
+ return gl::NoError();
+}
- gl::Box destArea(destOffset.x, destOffset.y, 0, sourceRect.width, sourceRect.height, 1);
- gl::Extents destSize(destRenderTarget->getWidth(), destRenderTarget->getHeight(), 1);
+gl::Error Renderer11::copyImage3D(const gl::Context *context,
+ const gl::Framebuffer *framebuffer,
+ const gl::Rectangle &sourceRect,
+ GLenum destFormat,
+ const gl::Offset &destOffset,
+ TextureStorage *storage,
+ GLint level)
+{
+ TextureStorage11_3D *storage11 = GetAs<TextureStorage11_3D>(storage);
+ ASSERT(storage11);
- // Use nearest filtering because source and destination are the same size for the direct
- // copy
- error = mBlit->copyTexture(source, sourceArea, sourceSize, dest, destArea, destSize, NULL,
- destFormat, GL_NEAREST, false);
- if (error.isError())
- {
- return error;
- }
+ gl::ImageIndex index = gl::ImageIndex::Make3D(level, destOffset.z);
+ RenderTargetD3D *destRenderTarget = nullptr;
+ ANGLE_TRY(storage11->getRenderTarget(context, index, &destRenderTarget));
+ ASSERT(destRenderTarget);
+
+ ANGLE_TRY(copyImageInternal(context, framebuffer, sourceRect, destFormat, destOffset,
+ destRenderTarget));
- storage11->invalidateSwizzleCacheLevel(level);
+ storage11->markLevelDirty(level);
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error Renderer11::copyImage3D(const gl::Framebuffer *framebuffer, const gl::Rectangle &sourceRect, GLenum destFormat,
- const gl::Offset &destOffset, TextureStorage *storage, GLint level)
+gl::Error Renderer11::copyImage2DArray(const gl::Context *context,
+ const gl::Framebuffer *framebuffer,
+ const gl::Rectangle &sourceRect,
+ GLenum destFormat,
+ const gl::Offset &destOffset,
+ TextureStorage *storage,
+ GLint level)
{
- const gl::FramebufferAttachment *colorbuffer = framebuffer->getReadColorbuffer();
- ASSERT(colorbuffer);
+ TextureStorage11_2DArray *storage11 = GetAs<TextureStorage11_2DArray>(storage);
+ ASSERT(storage11);
- RenderTarget11 *sourceRenderTarget = NULL;
- gl::Error error = colorbuffer->getRenderTarget(&sourceRenderTarget);
- if (error.isError())
- {
- return error;
- }
- ASSERT(sourceRenderTarget);
+ gl::ImageIndex index = gl::ImageIndex::Make2DArray(level, destOffset.z);
+ RenderTargetD3D *destRenderTarget = nullptr;
+ ANGLE_TRY(storage11->getRenderTarget(context, index, &destRenderTarget));
+ ASSERT(destRenderTarget);
- ID3D11ShaderResourceView *source = sourceRenderTarget->getShaderResourceView();
- ASSERT(source);
+ ANGLE_TRY(copyImageInternal(context, framebuffer, sourceRect, destFormat, destOffset,
+ destRenderTarget));
+ storage11->markLevelDirty(level);
- TextureStorage11_3D *storage11 = GetAs<TextureStorage11_3D>(storage);
- ASSERT(storage11);
+ return gl::NoError();
+}
- gl::ImageIndex index = gl::ImageIndex::Make3D(level, destOffset.z);
- RenderTargetD3D *destRenderTarget = NULL;
- error = storage11->getRenderTarget(index, &destRenderTarget);
- if (error.isError())
- {
- return error;
- }
- ASSERT(destRenderTarget);
+gl::Error Renderer11::copyTexture(const gl::Context *context,
+ const gl::Texture *source,
+ GLint sourceLevel,
+ const gl::Rectangle &sourceRect,
+ GLenum destFormat,
+ const gl::Offset &destOffset,
+ TextureStorage *storage,
+ GLenum destTarget,
+ GLint destLevel,
+ bool unpackFlipY,
+ bool unpackPremultiplyAlpha,
+ bool unpackUnmultiplyAlpha)
+{
+ TextureD3D *sourceD3D = GetImplAs<TextureD3D>(source);
- ID3D11RenderTargetView *dest = GetAs<RenderTarget11>(destRenderTarget)->getRenderTargetView();
- ASSERT(dest);
+ TextureStorage *sourceStorage = nullptr;
+ ANGLE_TRY(sourceD3D->getNativeTexture(context, &sourceStorage));
- gl::Box sourceArea(sourceRect.x, sourceRect.y, 0, sourceRect.width, sourceRect.height, 1);
- gl::Extents sourceSize(sourceRenderTarget->getWidth(), sourceRenderTarget->getHeight(), 1);
+ TextureStorage11_2D *sourceStorage11 = GetAs<TextureStorage11_2D>(sourceStorage);
+ ASSERT(sourceStorage11);
- gl::Box destArea(destOffset.x, destOffset.y, 0, sourceRect.width, sourceRect.height, 1);
- gl::Extents destSize(destRenderTarget->getWidth(), destRenderTarget->getHeight(), 1);
+ TextureStorage11 *destStorage11 = GetAs<TextureStorage11>(storage);
+ ASSERT(destStorage11);
- // Use nearest filtering because source and destination are the same size for the direct
- // copy
- error = mBlit->copyTexture(source, sourceArea, sourceSize, dest, destArea, destSize, NULL,
- destFormat, GL_NEAREST, false);
- if (error.isError())
+ // Check for fast path where a CopySubresourceRegion can be used.
+ if (unpackPremultiplyAlpha == unpackUnmultiplyAlpha && !unpackFlipY &&
+ source->getFormat(GL_TEXTURE_2D, sourceLevel).info->format == destFormat &&
+ sourceStorage11->getFormatSet().texFormat == destStorage11->getFormatSet().texFormat)
{
- return error;
- }
+ const TextureHelper11 *sourceResource = nullptr;
+ ANGLE_TRY(sourceStorage11->getResource(context, &sourceResource));
- storage11->invalidateSwizzleCacheLevel(level);
+ gl::ImageIndex sourceIndex = gl::ImageIndex::Make2D(sourceLevel);
+ UINT sourceSubresource = sourceStorage11->getSubresourceIndex(sourceIndex);
- return gl::Error(GL_NO_ERROR);
-}
+ const TextureHelper11 *destResource = nullptr;
+ ANGLE_TRY(destStorage11->getResource(context, &destResource));
-gl::Error Renderer11::copyImage2DArray(const gl::Framebuffer *framebuffer, const gl::Rectangle &sourceRect, GLenum destFormat,
- const gl::Offset &destOffset, TextureStorage *storage, GLint level)
-{
- const gl::FramebufferAttachment *colorbuffer = framebuffer->getReadColorbuffer();
- ASSERT(colorbuffer);
+ gl::ImageIndex destIndex = gl::ImageIndex::MakeGeneric(destTarget, destLevel);
+ UINT destSubresource = destStorage11->getSubresourceIndex(destIndex);
- RenderTarget11 *sourceRenderTarget = NULL;
- gl::Error error = colorbuffer->getRenderTarget(&sourceRenderTarget);
- if (error.isError())
- {
- return error;
+ D3D11_BOX sourceBox{
+ static_cast<UINT>(sourceRect.x),
+ static_cast<UINT>(sourceRect.y),
+ 0u,
+ static_cast<UINT>(sourceRect.x + sourceRect.width),
+ static_cast<UINT>(sourceRect.y + sourceRect.height),
+ 1u,
+ };
+
+ mDeviceContext->CopySubresourceRegion(destResource->get(), destSubresource, destOffset.x,
+ destOffset.y, destOffset.z, sourceResource->get(),
+ sourceSubresource, &sourceBox);
}
- ASSERT(sourceRenderTarget);
+ else
+ {
+ const d3d11::SharedSRV *sourceSRV = nullptr;
+ ANGLE_TRY(sourceStorage11->getSRVLevels(context, sourceLevel, sourceLevel, &sourceSRV));
- ID3D11ShaderResourceView *source = sourceRenderTarget->getShaderResourceView();
- ASSERT(source);
+ gl::ImageIndex destIndex = gl::ImageIndex::MakeGeneric(destTarget, destLevel);
+ RenderTargetD3D *destRenderTargetD3D = nullptr;
+ ANGLE_TRY(destStorage11->getRenderTarget(context, destIndex, &destRenderTargetD3D));
- TextureStorage11_2DArray *storage11 = GetAs<TextureStorage11_2DArray>(storage);
- ASSERT(storage11);
-
- gl::ImageIndex index = gl::ImageIndex::Make2DArray(level, destOffset.z);
- RenderTargetD3D *destRenderTarget = NULL;
- error = storage11->getRenderTarget(index, &destRenderTarget);
- if (error.isError())
- {
- return error;
- }
- ASSERT(destRenderTarget);
+ RenderTarget11 *destRenderTarget11 = GetAs<RenderTarget11>(destRenderTargetD3D);
- ID3D11RenderTargetView *dest = GetAs<RenderTarget11>(destRenderTarget)->getRenderTargetView();
- ASSERT(dest);
+ const d3d11::RenderTargetView &destRTV = destRenderTarget11->getRenderTargetView();
+ ASSERT(destRTV.valid());
- gl::Box sourceArea(sourceRect.x, sourceRect.y, 0, sourceRect.width, sourceRect.height, 1);
- gl::Extents sourceSize(sourceRenderTarget->getWidth(), sourceRenderTarget->getHeight(), 1);
+ gl::Box sourceArea(sourceRect.x, sourceRect.y, 0, sourceRect.width, sourceRect.height, 1);
+ gl::Extents sourceSize(
+ static_cast<int>(source->getWidth(source->getTarget(), sourceLevel)),
+ static_cast<int>(source->getHeight(source->getTarget(), sourceLevel)), 1);
+ if (unpackFlipY)
+ {
+ sourceArea.y += sourceArea.height;
+ sourceArea.height = -sourceArea.height;
+ }
- gl::Box destArea(destOffset.x, destOffset.y, 0, sourceRect.width, sourceRect.height, 1);
- gl::Extents destSize(destRenderTarget->getWidth(), destRenderTarget->getHeight(), 1);
+ gl::Box destArea(destOffset.x, destOffset.y, 0, sourceRect.width, sourceRect.height, 1);
+ gl::Extents destSize(destRenderTarget11->getWidth(), destRenderTarget11->getHeight(), 1);
- // Use nearest filtering because source and destination are the same size for the direct
- // copy
- error = mBlit->copyTexture(source, sourceArea, sourceSize, dest, destArea, destSize, NULL,
- destFormat, GL_NEAREST, false);
- if (error.isError())
- {
- return error;
+ // Use nearest filtering because source and destination are the same size for the direct
+ // copy
+ GLenum sourceFormat = source->getFormat(GL_TEXTURE_2D, sourceLevel).info->format;
+ ANGLE_TRY(mBlit->copyTexture(context, *sourceSRV, sourceArea, sourceSize, sourceFormat,
+ destRTV, destArea, destSize, nullptr, destFormat, GL_NEAREST,
+ false, unpackPremultiplyAlpha, unpackUnmultiplyAlpha));
}
- storage11->invalidateSwizzleCacheLevel(level);
+ destStorage11->markLevelDirty(destLevel);
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-void Renderer11::unapplyRenderTargets()
+gl::Error Renderer11::copyCompressedTexture(const gl::Context *context,
+ const gl::Texture *source,
+ GLint sourceLevel,
+ TextureStorage *storage,
+ GLint destLevel)
{
- setOneTimeRenderTarget(NULL);
-}
+ TextureStorage11_2D *destStorage11 = GetAs<TextureStorage11_2D>(storage);
+ ASSERT(destStorage11);
-// When finished with this rendertarget, markAllStateDirty must be called.
-void Renderer11::setOneTimeRenderTarget(ID3D11RenderTargetView *renderTargetView)
-{
- ID3D11RenderTargetView *rtvArray[gl::IMPLEMENTATION_MAX_DRAW_BUFFERS] = {NULL};
+ const TextureHelper11 *destResource = nullptr;
+ ANGLE_TRY(destStorage11->getResource(context, &destResource));
- rtvArray[0] = renderTargetView;
+ gl::ImageIndex destIndex = gl::ImageIndex::Make2D(destLevel);
+ UINT destSubresource = destStorage11->getSubresourceIndex(destIndex);
- mDeviceContext->OMSetRenderTargets(getRendererCaps().maxDrawBuffers, rtvArray, NULL);
+ TextureD3D *sourceD3D = GetImplAs<TextureD3D>(source);
+ ASSERT(sourceD3D);
- // Do not preserve the serial for this one-time-use render target
- for (size_t rtIndex = 0; rtIndex < ArraySize(mAppliedRTVs); rtIndex++)
- {
- mAppliedRTVs[rtIndex] = angle::DirtyPointer;
- }
- mAppliedDSV = angle::DirtyPointer;
+ TextureStorage *sourceStorage = nullptr;
+ ANGLE_TRY(sourceD3D->getNativeTexture(context, &sourceStorage));
+
+ TextureStorage11_2D *sourceStorage11 = GetAs<TextureStorage11_2D>(sourceStorage);
+ ASSERT(sourceStorage11);
+
+ const TextureHelper11 *sourceResource = nullptr;
+ ANGLE_TRY(sourceStorage11->getResource(context, &sourceResource));
+
+ gl::ImageIndex sourceIndex = gl::ImageIndex::Make2D(sourceLevel);
+ UINT sourceSubresource = sourceStorage11->getSubresourceIndex(sourceIndex);
+
+ mDeviceContext->CopySubresourceRegion(destResource->get(), destSubresource, 0, 0, 0,
+ sourceResource->get(), sourceSubresource, nullptr);
+
+ return gl::NoError();
}
-gl::Error Renderer11::createRenderTarget(int width, int height, GLenum format, GLsizei samples, RenderTargetD3D **outRT)
+gl::Error Renderer11::createRenderTarget(int width,
+ int height,
+ GLenum format,
+ GLsizei samples,
+ RenderTargetD3D **outRT)
{
- const d3d11::TextureFormat &formatInfo = d3d11::GetTextureFormatInfo(format, mRenderer11DeviceCaps);
+ const d3d11::Format &formatInfo = d3d11::Format::Get(format, mRenderer11DeviceCaps);
- const gl::TextureCaps &textureCaps = getRendererTextureCaps().get(format);
- GLuint supportedSamples = textureCaps.getNearestSamples(samples);
+ const gl::TextureCaps &textureCaps = getNativeTextureCaps().get(format);
+ GLuint supportedSamples = textureCaps.getNearestSamples(samples);
if (width > 0 && height > 0)
{
// Create texture resource
D3D11_TEXTURE2D_DESC desc;
- desc.Width = width;
- desc.Height = height;
- desc.MipLevels = 1;
- desc.ArraySize = 1;
- desc.Format = formatInfo.texFormat;
- desc.SampleDesc.Count = (supportedSamples == 0) ? 1 : supportedSamples;
+ desc.Width = width;
+ desc.Height = height;
+ desc.MipLevels = 1;
+ desc.ArraySize = 1;
+ desc.Format = formatInfo.texFormat;
+ desc.SampleDesc.Count = (supportedSamples == 0) ? 1 : supportedSamples;
desc.SampleDesc.Quality = 0;
- desc.Usage = D3D11_USAGE_DEFAULT;
- desc.CPUAccessFlags = 0;
- desc.MiscFlags = 0;
+ desc.Usage = D3D11_USAGE_DEFAULT;
+ desc.CPUAccessFlags = 0;
+ desc.MiscFlags = 0;
// If a rendertarget or depthstencil format exists for this texture format,
// we'll flag it to allow binding that way. Shader resource views are a little
@@ -2987,110 +2707,105 @@ gl::Error Renderer11::createRenderTarget(int width, int height, GLenum format, G
bool bindRTV = false, bindDSV = false, bindSRV = false;
bindRTV = (formatInfo.rtvFormat != DXGI_FORMAT_UNKNOWN);
bindDSV = (formatInfo.dsvFormat != DXGI_FORMAT_UNKNOWN);
- if (formatInfo.srvFormat != DXGI_FORMAT_UNKNOWN)
+ bindSRV = (formatInfo.srvFormat != DXGI_FORMAT_UNKNOWN);
+
+ bool isMultisampledDepthStencil = bindDSV && desc.SampleDesc.Count > 1;
+ if (isMultisampledDepthStencil &&
+ !mRenderer11DeviceCaps.supportsMultisampledDepthStencilSRVs)
{
- // Multisample targets flagged for binding as depth stencil cannot also be
- // flagged for binding as SRV, so make certain not to add the SRV flag for
- // these targets.
- bindSRV = !(formatInfo.dsvFormat != DXGI_FORMAT_UNKNOWN && desc.SampleDesc.Count > 1);
+ bindSRV = false;
}
- desc.BindFlags = (bindRTV ? D3D11_BIND_RENDER_TARGET : 0) |
- (bindDSV ? D3D11_BIND_DEPTH_STENCIL : 0) |
+ desc.BindFlags = (bindRTV ? D3D11_BIND_RENDER_TARGET : 0) |
+ (bindDSV ? D3D11_BIND_DEPTH_STENCIL : 0) |
(bindSRV ? D3D11_BIND_SHADER_RESOURCE : 0);
// The format must be either an RTV or a DSV
ASSERT(bindRTV != bindDSV);
- ID3D11Texture2D *texture = NULL;
- HRESULT result = mDevice->CreateTexture2D(&desc, NULL, &texture);
- if (FAILED(result))
- {
- ASSERT(result == E_OUTOFMEMORY);
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create render target texture, result: 0x%X.", result);
- }
+ TextureHelper11 texture;
+ ANGLE_TRY(allocateTexture(desc, formatInfo, &texture));
- ID3D11ShaderResourceView *srv = NULL;
+ d3d11::SharedSRV srv;
+ d3d11::SharedSRV blitSRV;
if (bindSRV)
{
D3D11_SHADER_RESOURCE_VIEW_DESC srvDesc;
- srvDesc.Format = formatInfo.srvFormat;
- srvDesc.ViewDimension = (supportedSamples == 0) ? D3D11_SRV_DIMENSION_TEXTURE2D : D3D11_SRV_DIMENSION_TEXTURE2DMS;
+ srvDesc.Format = formatInfo.srvFormat;
+ srvDesc.ViewDimension = (supportedSamples == 0) ? D3D11_SRV_DIMENSION_TEXTURE2D
+ : D3D11_SRV_DIMENSION_TEXTURE2DMS;
srvDesc.Texture2D.MostDetailedMip = 0;
- srvDesc.Texture2D.MipLevels = 1;
+ srvDesc.Texture2D.MipLevels = 1;
- result = mDevice->CreateShaderResourceView(texture, &srvDesc, &srv);
- if (FAILED(result))
+ ANGLE_TRY(allocateResource(srvDesc, texture.get(), &srv));
+
+ if (formatInfo.blitSRVFormat != formatInfo.srvFormat)
{
- ASSERT(result == E_OUTOFMEMORY);
- SafeRelease(texture);
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create render target shader resource view, result: 0x%X.", result);
+ D3D11_SHADER_RESOURCE_VIEW_DESC blitSRVDesc;
+ blitSRVDesc.Format = formatInfo.blitSRVFormat;
+ blitSRVDesc.ViewDimension = (supportedSamples == 0)
+ ? D3D11_SRV_DIMENSION_TEXTURE2D
+ : D3D11_SRV_DIMENSION_TEXTURE2DMS;
+ blitSRVDesc.Texture2D.MostDetailedMip = 0;
+ blitSRVDesc.Texture2D.MipLevels = 1;
+
+ ANGLE_TRY(allocateResource(blitSRVDesc, texture.get(), &blitSRV));
+ }
+ else
+ {
+ blitSRV = srv.makeCopy();
}
}
if (bindDSV)
{
D3D11_DEPTH_STENCIL_VIEW_DESC dsvDesc;
- dsvDesc.Format = formatInfo.dsvFormat;
- dsvDesc.ViewDimension = (supportedSamples == 0) ? D3D11_DSV_DIMENSION_TEXTURE2D : D3D11_DSV_DIMENSION_TEXTURE2DMS;
+ dsvDesc.Format = formatInfo.dsvFormat;
+ dsvDesc.ViewDimension = (supportedSamples == 0) ? D3D11_DSV_DIMENSION_TEXTURE2D
+ : D3D11_DSV_DIMENSION_TEXTURE2DMS;
dsvDesc.Texture2D.MipSlice = 0;
- dsvDesc.Flags = 0;
+ dsvDesc.Flags = 0;
- ID3D11DepthStencilView *dsv = NULL;
- result = mDevice->CreateDepthStencilView(texture, &dsvDesc, &dsv);
- if (FAILED(result))
- {
- ASSERT(result == E_OUTOFMEMORY);
- SafeRelease(texture);
- SafeRelease(srv);
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create render target depth stencil view, result: 0x%X.", result);
- }
+ d3d11::DepthStencilView dsv;
+ ANGLE_TRY(allocateResource(dsvDesc, texture.get(), &dsv));
- *outRT = new TextureRenderTarget11(dsv, texture, srv, format, width, height, 1, supportedSamples);
-
- SafeRelease(dsv);
+ *outRT = new TextureRenderTarget11(std::move(dsv), texture, srv, format, formatInfo,
+ width, height, 1, supportedSamples);
}
else if (bindRTV)
{
D3D11_RENDER_TARGET_VIEW_DESC rtvDesc;
- rtvDesc.Format = formatInfo.rtvFormat;
- rtvDesc.ViewDimension = (supportedSamples == 0) ? D3D11_RTV_DIMENSION_TEXTURE2D : D3D11_RTV_DIMENSION_TEXTURE2DMS;
+ rtvDesc.Format = formatInfo.rtvFormat;
+ rtvDesc.ViewDimension = (supportedSamples == 0) ? D3D11_RTV_DIMENSION_TEXTURE2D
+ : D3D11_RTV_DIMENSION_TEXTURE2DMS;
rtvDesc.Texture2D.MipSlice = 0;
- ID3D11RenderTargetView *rtv = NULL;
- result = mDevice->CreateRenderTargetView(texture, &rtvDesc, &rtv);
- if (FAILED(result))
- {
- ASSERT(result == E_OUTOFMEMORY);
- SafeRelease(texture);
- SafeRelease(srv);
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create render target render target view, result: 0x%X.", result);
- }
+ d3d11::RenderTargetView rtv;
+ ANGLE_TRY(allocateResource(rtvDesc, texture.get(), &rtv));
- if (formatInfo.dataInitializerFunction != NULL)
+ if (formatInfo.dataInitializerFunction != nullptr)
{
- const float clearValues[4] = { 0.0f, 0.0f, 0.0f, 1.0f };
- mDeviceContext->ClearRenderTargetView(rtv, clearValues);
+ const float clearValues[4] = {0.0f, 0.0f, 0.0f, 1.0f};
+ mDeviceContext->ClearRenderTargetView(rtv.get(), clearValues);
}
- *outRT = new TextureRenderTarget11(rtv, texture, srv, format, width, height, 1, supportedSamples);
-
- SafeRelease(rtv);
+ *outRT = new TextureRenderTarget11(std::move(rtv), texture, srv, blitSRV, format,
+ formatInfo, width, height, 1, supportedSamples);
}
else
{
UNREACHABLE();
}
-
- SafeRelease(texture);
- SafeRelease(srv);
}
else
{
- *outRT = new TextureRenderTarget11(reinterpret_cast<ID3D11RenderTargetView*>(NULL), NULL, NULL, format, width, height, 1, supportedSamples);
+ *outRT = new TextureRenderTarget11(d3d11::RenderTargetView(), TextureHelper11(),
+ d3d11::SharedSRV(), d3d11::SharedSRV(), format,
+ d3d11::Format::Get(GL_NONE, mRenderer11DeviceCaps),
+ width, height, 1, supportedSamples);
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
gl::Error Renderer11::createRenderTargetCopy(RenderTargetD3D *source, RenderTargetD3D **outRT)
@@ -3098,58 +2813,35 @@ gl::Error Renderer11::createRenderTargetCopy(RenderTargetD3D *source, RenderTarg
ASSERT(source != nullptr);
RenderTargetD3D *newRT = nullptr;
- gl::Error error = createRenderTarget(source->getWidth(), source->getHeight(),
- source->getInternalFormat(), source->getSamples(), &newRT);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(createRenderTarget(source->getWidth(), source->getHeight(),
+ source->getInternalFormat(), source->getSamples(), &newRT));
RenderTarget11 *source11 = GetAs<RenderTarget11>(source);
RenderTarget11 *dest11 = GetAs<RenderTarget11>(newRT);
- mDeviceContext->CopySubresourceRegion(dest11->getTexture(), dest11->getSubresourceIndex(), 0, 0,
- 0, source11->getTexture(),
+ mDeviceContext->CopySubresourceRegion(dest11->getTexture().get(), dest11->getSubresourceIndex(),
+ 0, 0, 0, source11->getTexture().get(),
source11->getSubresourceIndex(), nullptr);
*outRT = newRT;
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-FramebufferImpl *Renderer11::createFramebuffer(const gl::Framebuffer::Data &data)
-{
- return new Framebuffer11(data, this);
-}
-
-ShaderImpl *Renderer11::createShader(const gl::Shader::Data &data)
-{
- return new ShaderD3D(data);
-}
-
-ProgramImpl *Renderer11::createProgram(const gl::Program::Data &data)
-{
- return new ProgramD3D(data, this);
-}
-
-gl::Error Renderer11::loadExecutable(const void *function,
+gl::Error Renderer11::loadExecutable(const uint8_t *function,
size_t length,
- ShaderType type,
+ gl::ShaderType type,
const std::vector<D3DVarying> &streamOutVaryings,
bool separatedOutputBuffers,
ShaderExecutableD3D **outExecutable)
{
+ ShaderData shaderData(function, length);
+
switch (type)
{
- case SHADER_VERTEX:
+ case gl::SHADER_VERTEX:
{
- ID3D11VertexShader *vertexShader = NULL;
- ID3D11GeometryShader *streamOutShader = NULL;
-
- HRESULT result = mDevice->CreateVertexShader(function, length, NULL, &vertexShader);
- ASSERT(SUCCEEDED(result));
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create vertex shader, result: 0x%X.", result);
- }
+ d3d11::VertexShader vertexShader;
+ d3d11::GeometryShader streamOutShader;
+ ANGLE_TRY(allocateResource(shaderData, &vertexShader));
if (!streamOutVaryings.empty())
{
@@ -3163,88 +2855,80 @@ gl::Error Renderer11::loadExecutable(const void *function,
entry.SemanticName = streamOutVarying.semanticName.c_str();
entry.SemanticIndex = streamOutVarying.semanticIndex;
entry.StartComponent = 0;
- entry.ComponentCount = static_cast<BYTE>(streamOutVarying.componentCount);
- entry.OutputSlot = static_cast<BYTE>(
+ entry.ComponentCount = static_cast<BYTE>(streamOutVarying.componentCount);
+ entry.OutputSlot = static_cast<BYTE>(
(separatedOutputBuffers ? streamOutVarying.outputSlot : 0));
soDeclaration.push_back(entry);
}
- result = mDevice->CreateGeometryShaderWithStreamOutput(
- function, static_cast<unsigned int>(length), soDeclaration.data(),
- static_cast<unsigned int>(soDeclaration.size()), NULL, 0, 0, NULL,
- &streamOutShader);
- ASSERT(SUCCEEDED(result));
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create steam output shader, result: 0x%X.", result);
- }
+ ANGLE_TRY(allocateResource(shaderData, &soDeclaration, &streamOutShader));
}
- *outExecutable = new ShaderExecutable11(function, length, vertexShader, streamOutShader);
+ *outExecutable = new ShaderExecutable11(function, length, std::move(vertexShader),
+ std::move(streamOutShader));
}
break;
- case SHADER_PIXEL:
+ case gl::SHADER_FRAGMENT:
{
- ID3D11PixelShader *pixelShader = NULL;
-
- HRESULT result = mDevice->CreatePixelShader(function, length, NULL, &pixelShader);
- ASSERT(SUCCEEDED(result));
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create pixel shader, result: 0x%X.", result);
- }
-
- *outExecutable = new ShaderExecutable11(function, length, pixelShader);
+ d3d11::PixelShader pixelShader;
+ ANGLE_TRY(allocateResource(shaderData, &pixelShader));
+ *outExecutable = new ShaderExecutable11(function, length, std::move(pixelShader));
}
break;
- case SHADER_GEOMETRY:
+ case gl::SHADER_GEOMETRY:
{
- ID3D11GeometryShader *geometryShader = NULL;
-
- HRESULT result = mDevice->CreateGeometryShader(function, length, NULL, &geometryShader);
- ASSERT(SUCCEEDED(result));
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create geometry shader, result: 0x%X.", result);
- }
-
- *outExecutable = new ShaderExecutable11(function, length, geometryShader);
+ d3d11::GeometryShader geometryShader;
+ ANGLE_TRY(allocateResource(shaderData, &geometryShader));
+ *outExecutable = new ShaderExecutable11(function, length, std::move(geometryShader));
+ }
+ break;
+ case gl::SHADER_COMPUTE:
+ {
+ d3d11::ComputeShader computeShader;
+ ANGLE_TRY(allocateResource(shaderData, &computeShader));
+ *outExecutable = new ShaderExecutable11(function, length, std::move(computeShader));
}
break;
- default:
- UNREACHABLE();
- return gl::Error(GL_INVALID_OPERATION);
+ default:
+ UNREACHABLE();
+ return gl::InternalError();
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
gl::Error Renderer11::compileToExecutable(gl::InfoLog &infoLog,
const std::string &shaderHLSL,
- ShaderType type,
+ gl::ShaderType type,
const std::vector<D3DVarying> &streamOutVaryings,
bool separatedOutputBuffers,
- const D3DCompilerWorkarounds &workarounds,
+ const angle::CompilerWorkaroundsD3D &workarounds,
ShaderExecutableD3D **outExectuable)
{
- const char *profileType = NULL;
+ std::stringstream profileStream;
+
switch (type)
{
- case SHADER_VERTEX:
- profileType = "vs";
- break;
- case SHADER_PIXEL:
- profileType = "ps";
- break;
- case SHADER_GEOMETRY:
- profileType = "gs";
- break;
- default:
- UNREACHABLE();
- return gl::Error(GL_INVALID_OPERATION);
+ case gl::SHADER_VERTEX:
+ profileStream << "vs";
+ break;
+ case gl::SHADER_FRAGMENT:
+ profileStream << "ps";
+ break;
+ case gl::SHADER_GEOMETRY:
+ profileStream << "gs";
+ break;
+ case gl::SHADER_COMPUTE:
+ profileStream << "cs";
+ break;
+ default:
+ UNREACHABLE();
+ return gl::InternalError();
}
- std::string profile = FormatString("%s_%d_%d%s", profileType, getMajorShaderModel(), getMinorShaderModel(), getShaderModelSuffix().c_str());
+ profileStream << "_" << getMajorShaderModel() << "_" << getMinorShaderModel()
+ << getShaderModelSuffix();
+ std::string profile = profileStream.str();
UINT flags = D3DCOMPILE_OPTIMIZATION_LEVEL2;
@@ -3260,11 +2944,12 @@ gl::Error Renderer11::compileToExecutable(gl::InfoLog &infoLog,
if (workarounds.enableIEEEStrictness)
flags |= D3DCOMPILE_IEEE_STRICTNESS;
- // Sometimes D3DCompile will fail with the default compilation flags for complicated shaders when it would otherwise pass with alternative options.
+ // Sometimes D3DCompile will fail with the default compilation flags for complicated shaders
+ // when it would otherwise pass with alternative options.
// Try the default flags first and if compilation fails, try some alternatives.
std::vector<CompileConfig> configs;
- configs.push_back(CompileConfig(flags, "default" ));
- configs.push_back(CompileConfig(flags | D3DCOMPILE_SKIP_VALIDATION, "skip validation" ));
+ configs.push_back(CompileConfig(flags, "default"));
+ configs.push_back(CompileConfig(flags | D3DCOMPILE_SKIP_VALIDATION, "skip validation"));
configs.push_back(CompileConfig(flags | D3DCOMPILE_SKIP_OPTIMIZATION, "skip optimization"));
if (getMajorShaderModel() == 4 && getShaderModelSuffix() != "")
@@ -3276,26 +2961,26 @@ gl::Error Renderer11::compileToExecutable(gl::InfoLog &infoLog,
CompileConfig(flags | D3DCOMPILE_AVOID_FLOW_CONTROL, "avoid flow control"));
}
- D3D_SHADER_MACRO loopMacros[] = { {"ANGLE_ENABLE_LOOP_FLATTEN", "1"}, {0, 0} };
+ D3D_SHADER_MACRO loopMacros[] = {{"ANGLE_ENABLE_LOOP_FLATTEN", "1"}, {0, 0}};
- ID3DBlob *binary = NULL;
+ // TODO(jmadill): Use ComPtr?
+ ID3DBlob *binary = nullptr;
std::string debugInfo;
- gl::Error error = mCompiler.compileToBinary(infoLog, shaderHLSL, profile, configs, loopMacros, &binary, &debugInfo);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(mCompiler.compileToBinary(infoLog, shaderHLSL, profile, configs, loopMacros, &binary,
+ &debugInfo));
- // It's possible that binary is NULL if the compiler failed in all configurations. Set the executable to NULL
- // and return GL_NO_ERROR to signify that there was a link error but the internal state is still OK.
+ // It's possible that binary is NULL if the compiler failed in all configurations. Set the
+ // executable to NULL and return GL_NO_ERROR to signify that there was a link error but the
+ // internal state is still OK.
if (!binary)
{
- *outExectuable = NULL;
- return gl::Error(GL_NO_ERROR);
+ *outExectuable = nullptr;
+ return gl::NoError();
}
- error = loadExecutable(binary->GetBufferPointer(), binary->GetBufferSize(), type,
- streamOutVaryings, separatedOutputBuffers, outExectuable);
+ gl::Error error = loadExecutable(reinterpret_cast<const uint8_t *>(binary->GetBufferPointer()),
+ binary->GetBufferSize(), type, streamOutVaryings,
+ separatedOutputBuffers, outExectuable);
SafeRelease(binary);
if (error.isError())
@@ -3308,12 +2993,17 @@ gl::Error Renderer11::compileToExecutable(gl::InfoLog &infoLog,
(*outExectuable)->appendDebugInfo(debugInfo);
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
+}
+
+gl::Error Renderer11::ensureHLSLCompilerInitialized()
+{
+ return mCompiler.ensureInitialized();
}
UniformStorageD3D *Renderer11::createUniformStorage(size_t storageSize)
{
- return new UniformStorage11(this, storageSize);
+ return new UniformStorage11(storageSize);
}
VertexBuffer *Renderer11::createVertexBuffer()
@@ -3326,45 +3016,20 @@ IndexBuffer *Renderer11::createIndexBuffer()
return new IndexBuffer11(this);
}
-BufferImpl *Renderer11::createBuffer()
-{
- Buffer11 *buffer = new Buffer11(this);
- mAliveBuffers.insert(buffer);
- return buffer;
-}
-
-VertexArrayImpl *Renderer11::createVertexArray(const gl::VertexArray::Data &data)
-{
- return new VertexArray11(data);
-}
-
-QueryImpl *Renderer11::createQuery(GLenum type)
+StreamProducerImpl *Renderer11::createStreamProducerD3DTextureNV12(
+ egl::Stream::ConsumerType consumerType,
+ const egl::AttributeMap &attribs)
{
- return new Query11(this, type);
-}
-
-FenceNVImpl *Renderer11::createFenceNV()
-{
- return new FenceNV11(this);
-}
-
-FenceSyncImpl *Renderer11::createFenceSync()
-{
- return new FenceSync11(this);
-}
-
-TransformFeedbackImpl* Renderer11::createTransformFeedback()
-{
- return new TransformFeedbackD3D();
+ return new StreamProducerNV12(this);
}
bool Renderer11::supportsFastCopyBufferToTexture(GLenum internalFormat) const
{
- ASSERT(getRendererExtensions().pixelBufferObject);
+ ASSERT(getNativeExtensions().pixelBufferObject);
- const gl::InternalFormat &internalFormatInfo = gl::GetInternalFormatInfo(internalFormat);
- const d3d11::TextureFormat &d3d11FormatInfo = d3d11::GetTextureFormatInfo(internalFormat, mRenderer11DeviceCaps);
- const d3d11::DXGIFormat &dxgiFormatInfo = d3d11::GetDXGIFormatInfo(d3d11FormatInfo.texFormat);
+ const gl::InternalFormat &internalFormatInfo = gl::GetSizedInternalFormatInfo(internalFormat);
+ const d3d11::Format &d3d11FormatInfo =
+ d3d11::Format::Get(internalFormat, mRenderer11DeviceCaps);
// sRGB formats do not work with D3D11 buffer SRVs
if (internalFormatInfo.colorEncoding == GL_SRGB)
@@ -3385,7 +3050,19 @@ bool Renderer11::supportsFastCopyBufferToTexture(GLenum internalFormat) const
}
// We don't support formats which we can't represent without conversion
- if (dxgiFormatInfo.internalFormat != internalFormat)
+ if (d3d11FormatInfo.format().glInternalFormat != internalFormat)
+ {
+ return false;
+ }
+
+ // Buffer SRV creation for this format was not working on Windows 10.
+ if (d3d11FormatInfo.texFormat == DXGI_FORMAT_B5G5R5A1_UNORM)
+ {
+ return false;
+ }
+
+ // This format is not supported as a buffer SRV.
+ if (d3d11FormatInfo.texFormat == DXGI_FORMAT_A8_UNORM)
{
return false;
}
@@ -3393,11 +3070,17 @@ bool Renderer11::supportsFastCopyBufferToTexture(GLenum internalFormat) const
return true;
}
-gl::Error Renderer11::fastCopyBufferToTexture(const gl::PixelUnpackState &unpack, unsigned int offset, RenderTargetD3D *destRenderTarget,
- GLenum destinationFormat, GLenum sourcePixelsType, const gl::Box &destArea)
+gl::Error Renderer11::fastCopyBufferToTexture(const gl::Context *context,
+ const gl::PixelUnpackState &unpack,
+ unsigned int offset,
+ RenderTargetD3D *destRenderTarget,
+ GLenum destinationFormat,
+ GLenum sourcePixelsType,
+ const gl::Box &destArea)
{
ASSERT(supportsFastCopyBufferToTexture(destinationFormat));
- return mPixelTransfer->copyBufferToTexture(unpack, offset, destRenderTarget, destinationFormat, sourcePixelsType, destArea);
+ return mPixelTransfer->copyBufferToTexture(context, unpack, offset, destRenderTarget,
+ destinationFormat, sourcePixelsType, destArea);
}
ImageD3D *Renderer11::createImage()
@@ -3405,31 +3088,44 @@ ImageD3D *Renderer11::createImage()
return new Image11(this);
}
-gl::Error Renderer11::generateMipmap(ImageD3D *dest, ImageD3D *src)
+gl::Error Renderer11::generateMipmap(const gl::Context *context, ImageD3D *dest, ImageD3D *src)
{
Image11 *dest11 = GetAs<Image11>(dest);
- Image11 *src11 = GetAs<Image11>(src);
- return Image11::generateMipmap(dest11, src11);
+ Image11 *src11 = GetAs<Image11>(src);
+ return Image11::GenerateMipmap(context, dest11, src11, mRenderer11DeviceCaps);
}
-gl::Error Renderer11::generateMipmapsUsingD3D(TextureStorage *storage,
- const gl::TextureState &textureState)
+gl::Error Renderer11::generateMipmapUsingD3D(const gl::Context *context,
+ TextureStorage *storage,
+ const gl::TextureState &textureState)
{
TextureStorage11 *storage11 = GetAs<TextureStorage11>(storage);
ASSERT(storage11->isRenderTarget());
ASSERT(storage11->supportsNativeMipmapFunction());
- ID3D11ShaderResourceView *srv;
- gl::Error error = storage11->getSRVLevels(textureState.baseLevel, textureState.maxLevel, &srv);
- if (error.isError())
- {
- return error;
- }
+ const d3d11::SharedSRV *srv = nullptr;
+ ANGLE_TRY(storage11->getSRVLevels(context, textureState.getEffectiveBaseLevel(),
+ textureState.getEffectiveMaxLevel(), &srv));
- mDeviceContext->GenerateMips(srv);
+ mDeviceContext->GenerateMips(srv->get());
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
+}
+
+gl::Error Renderer11::copyImage(const gl::Context *context,
+ ImageD3D *dest,
+ ImageD3D *source,
+ const gl::Rectangle &sourceRect,
+ const gl::Offset &destOffset,
+ bool unpackFlipY,
+ bool unpackPremultiplyAlpha,
+ bool unpackUnmultiplyAlpha)
+{
+ Image11 *dest11 = GetAs<Image11>(dest);
+ Image11 *src11 = GetAs<Image11>(source);
+ return Image11::CopyImage(context, dest11, src11, sourceRect, destOffset, unpackFlipY,
+ unpackPremultiplyAlpha, unpackUnmultiplyAlpha, mRenderer11DeviceCaps);
}
TextureStorage *Renderer11::createTextureStorage2D(SwapChainD3D *swapChain)
@@ -3438,53 +3134,75 @@ TextureStorage *Renderer11::createTextureStorage2D(SwapChainD3D *swapChain)
return new TextureStorage11_2D(this, swapChain11);
}
-TextureStorage *Renderer11::createTextureStorageEGLImage(EGLImageD3D *eglImage)
+TextureStorage *Renderer11::createTextureStorageEGLImage(EGLImageD3D *eglImage,
+ RenderTargetD3D *renderTargetD3D)
{
- return new TextureStorage11_EGLImage(this, eglImage);
+ return new TextureStorage11_EGLImage(this, eglImage, GetAs<RenderTarget11>(renderTargetD3D));
}
-TextureStorage *Renderer11::createTextureStorage2D(GLenum internalformat, bool renderTarget, GLsizei width, GLsizei height, int levels, bool hintLevelZeroOnly)
+TextureStorage *Renderer11::createTextureStorageExternal(
+ egl::Stream *stream,
+ const egl::Stream::GLTextureDescription &desc)
{
- return new TextureStorage11_2D(this, internalformat, renderTarget, width, height, levels, hintLevelZeroOnly);
+ return new TextureStorage11_External(this, stream, desc);
}
-TextureStorage *Renderer11::createTextureStorageCube(GLenum internalformat, bool renderTarget, int size, int levels, bool hintLevelZeroOnly)
+TextureStorage *Renderer11::createTextureStorage2D(GLenum internalformat,
+ bool renderTarget,
+ GLsizei width,
+ GLsizei height,
+ int levels,
+ bool hintLevelZeroOnly)
{
- return new TextureStorage11_Cube(this, internalformat, renderTarget, size, levels, hintLevelZeroOnly);
+ return new TextureStorage11_2D(this, internalformat, renderTarget, width, height, levels,
+ hintLevelZeroOnly);
}
-TextureStorage *Renderer11::createTextureStorage3D(GLenum internalformat, bool renderTarget, GLsizei width, GLsizei height, GLsizei depth, int levels)
+TextureStorage *Renderer11::createTextureStorageCube(GLenum internalformat,
+ bool renderTarget,
+ int size,
+ int levels,
+ bool hintLevelZeroOnly)
{
- return new TextureStorage11_3D(this, internalformat, renderTarget, width, height, depth, levels);
+ return new TextureStorage11_Cube(this, internalformat, renderTarget, size, levels,
+ hintLevelZeroOnly);
}
-TextureStorage *Renderer11::createTextureStorage2DArray(GLenum internalformat, bool renderTarget, GLsizei width, GLsizei height, GLsizei depth, int levels)
+TextureStorage *Renderer11::createTextureStorage3D(GLenum internalformat,
+ bool renderTarget,
+ GLsizei width,
+ GLsizei height,
+ GLsizei depth,
+ int levels)
{
- return new TextureStorage11_2DArray(this, internalformat, renderTarget, width, height, depth, levels);
+ return new TextureStorage11_3D(this, internalformat, renderTarget, width, height, depth,
+ levels);
}
-TextureImpl *Renderer11::createTexture(GLenum target)
+TextureStorage *Renderer11::createTextureStorage2DArray(GLenum internalformat,
+ bool renderTarget,
+ GLsizei width,
+ GLsizei height,
+ GLsizei depth,
+ int levels)
{
- switch(target)
- {
- case GL_TEXTURE_2D: return new TextureD3D_2D(this);
- case GL_TEXTURE_CUBE_MAP: return new TextureD3D_Cube(this);
- case GL_TEXTURE_3D: return new TextureD3D_3D(this);
- case GL_TEXTURE_2D_ARRAY: return new TextureD3D_2DArray(this);
- default:
- UNREACHABLE();
- }
-
- return NULL;
+ return new TextureStorage11_2DArray(this, internalformat, renderTarget, width, height, depth,
+ levels);
}
-RenderbufferImpl *Renderer11::createRenderbuffer()
+TextureStorage *Renderer11::createTextureStorage2DMultisample(GLenum internalformat,
+ GLsizei width,
+ GLsizei height,
+ int levels,
+ int samples,
+ bool fixedSampleLocations)
{
- RenderbufferD3D *renderbuffer = new RenderbufferD3D(this);
- return renderbuffer;
+ return new TextureStorage11_2DMultisample(this, internalformat, width, height, levels, samples,
+ fixedSampleLocations);
}
-gl::Error Renderer11::readFromAttachment(const gl::FramebufferAttachment &srcAttachment,
+gl::Error Renderer11::readFromAttachment(const gl::Context *context,
+ const gl::FramebufferAttachment &srcAttachment,
const gl::Rectangle &sourceArea,
GLenum format,
GLenum type,
@@ -3497,17 +3215,11 @@ gl::Error Renderer11::readFromAttachment(const gl::FramebufferAttachment &srcAtt
const bool invertTexture = UsePresentPathFast(this, &srcAttachment);
- RenderTargetD3D *renderTarget = nullptr;
- gl::Error error = srcAttachment.getRenderTarget(&renderTarget);
- if (error.isError())
- {
- return error;
- }
+ RenderTarget11 *rt11 = nullptr;
+ ANGLE_TRY(srcAttachment.getRenderTarget(context, &rt11));
+ ASSERT(rt11->getTexture().valid());
- RenderTarget11 *rt11 = GetAs<RenderTarget11>(renderTarget);
- ASSERT(rt11->getTexture());
-
- TextureHelper11 textureHelper = TextureHelper11::MakeAndReference(rt11->getTexture());
+ const TextureHelper11 &textureHelper = rt11->getTexture();
unsigned int sourceSubResource = rt11->getSubresourceIndex();
const gl::Extents &texSize = textureHelper.getExtents();
@@ -3535,52 +3247,42 @@ gl::Error Renderer11::readFromAttachment(const gl::FramebufferAttachment &srcAtt
if (safeArea.width == 0 || safeArea.height == 0)
{
// no work to do
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
gl::Extents safeSize(safeArea.width, safeArea.height, 1);
- auto errorOrResult = CreateStagingTexture(textureHelper.getTextureType(),
- textureHelper.getFormat(), safeSize, mDevice);
- if (errorOrResult.isError())
- {
- return errorOrResult.getError();
- }
+ TextureHelper11 stagingHelper;
+ ANGLE_TRY_RESULT(
+ createStagingTexture(textureHelper.getTextureType(), textureHelper.getFormatSet(), safeSize,
+ StagingAccess::READ),
+ stagingHelper);
- TextureHelper11 stagingHelper(errorOrResult.getResult());
TextureHelper11 resolvedTextureHelper;
// "srcTexture" usually points to the source texture.
// For 2D multisampled textures, it points to the multisampled resolve texture.
const TextureHelper11 *srcTexture = &textureHelper;
- if (textureHelper.getTextureType() == GL_TEXTURE_2D && textureHelper.getSampleCount() > 1)
+ if (textureHelper.is2D() && textureHelper.getSampleCount() > 1)
{
D3D11_TEXTURE2D_DESC resolveDesc;
resolveDesc.Width = static_cast<UINT>(texSize.width);
resolveDesc.Height = static_cast<UINT>(texSize.height);
- resolveDesc.MipLevels = 1;
- resolveDesc.ArraySize = 1;
+ resolveDesc.MipLevels = 1;
+ resolveDesc.ArraySize = 1;
resolveDesc.Format = textureHelper.getFormat();
- resolveDesc.SampleDesc.Count = 1;
+ resolveDesc.SampleDesc.Count = 1;
resolveDesc.SampleDesc.Quality = 0;
- resolveDesc.Usage = D3D11_USAGE_DEFAULT;
- resolveDesc.BindFlags = 0;
- resolveDesc.CPUAccessFlags = 0;
- resolveDesc.MiscFlags = 0;
+ resolveDesc.Usage = D3D11_USAGE_DEFAULT;
+ resolveDesc.BindFlags = 0;
+ resolveDesc.CPUAccessFlags = 0;
+ resolveDesc.MiscFlags = 0;
- ID3D11Texture2D *resolveTex2D = nullptr;
- HRESULT result = mDevice->CreateTexture2D(&resolveDesc, nullptr, &resolveTex2D);
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY,
- "Renderer11::readTextureData failed to create internal resolve "
- "texture for ReadPixels, HRESULT: 0x%X.",
- result);
- }
+ ANGLE_TRY(
+ allocateTexture(resolveDesc, textureHelper.getFormatSet(), &resolvedTextureHelper));
- mDeviceContext->ResolveSubresource(resolveTex2D, 0, textureHelper.getTexture2D(),
+ mDeviceContext->ResolveSubresource(resolvedTextureHelper.get(), 0, textureHelper.get(),
sourceSubResource, textureHelper.getFormat());
- resolvedTextureHelper = TextureHelper11::MakeAndReference(resolveTex2D);
sourceSubResource = 0;
srcTexture = &resolvedTextureHelper;
@@ -3594,132 +3296,66 @@ gl::Error Renderer11::readFromAttachment(const gl::FramebufferAttachment &srcAtt
// Select the correct layer from a 3D attachment
srcBox.front = 0;
- if (textureHelper.getTextureType() == GL_TEXTURE_3D)
+ if (textureHelper.is3D())
{
srcBox.front = static_cast<UINT>(srcAttachment.layer());
}
srcBox.back = srcBox.front + 1;
- mDeviceContext->CopySubresourceRegion(stagingHelper.getResource(), 0, 0, 0, 0,
- srcTexture->getResource(), sourceSubResource, &srcBox);
-
- if (invertTexture)
- {
- gl::PixelPackState invertTexturePack;
-
- // Create a new PixelPackState with reversed row order. Note that we can't just assign
- // 'invertTexturePack' to be 'pack' (or memcpy) since that breaks the ref counting/object
- // tracking in the 'pixelBuffer' members, causing leaks. Instead we must use
- // pixelBuffer.set() twice, which performs the addRef/release correctly
- invertTexturePack.alignment = pack.alignment;
- invertTexturePack.pixelBuffer.set(pack.pixelBuffer.get());
- invertTexturePack.reverseRowOrder = !pack.reverseRowOrder;
-
- PackPixelsParams packParams(safeArea, format, type, outputPitch, invertTexturePack, 0);
- error = packPixels(stagingHelper, packParams, pixelsOut);
-
- invertTexturePack.pixelBuffer.set(nullptr);
+ mDeviceContext->CopySubresourceRegion(stagingHelper.get(), 0, 0, 0, 0, srcTexture->get(),
+ sourceSubResource, &srcBox);
- return error;
- }
- else
+ gl::Buffer *packBuffer = context->getGLState().getTargetBuffer(gl::BufferBinding::PixelPack);
+ if (!invertTexture)
{
- PackPixelsParams packParams(safeArea, format, type, outputPitch, pack, 0);
+ PackPixelsParams packParams(safeArea, format, type, outputPitch, pack, packBuffer, 0);
return packPixels(stagingHelper, packParams, pixelsOut);
}
+
+ // Create a new PixelPackState with reversed row order. Note that we can't just assign
+ // 'invertTexturePack' to be 'pack' (or memcpy) since that breaks the ref counting/object
+ // tracking in the 'pixelBuffer' members, causing leaks. Instead we must use
+ // pixelBuffer.set() twice, which performs the addRef/release correctly
+ gl::PixelPackState invertTexturePack;
+ invertTexturePack.alignment = pack.alignment;
+ invertTexturePack.reverseRowOrder = !pack.reverseRowOrder;
+
+ PackPixelsParams packParams(safeArea, format, type, outputPitch, invertTexturePack, packBuffer,
+ 0);
+ gl::Error error = packPixels(stagingHelper, packParams, pixelsOut);
+ ANGLE_TRY(error);
+ return gl::NoError();
}
gl::Error Renderer11::packPixels(const TextureHelper11 &textureHelper,
const PackPixelsParams &params,
uint8_t *pixelsOut)
{
- ID3D11Resource *readResource = textureHelper.getResource();
+ ID3D11Resource *readResource = textureHelper.get();
D3D11_MAPPED_SUBRESOURCE mapping;
HRESULT hr = mDeviceContext->Map(readResource, 0, D3D11_MAP_READ, 0, &mapping);
if (FAILED(hr))
{
ASSERT(hr == E_OUTOFMEMORY);
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to map internal texture for reading, result: 0x%X.", hr);
- }
-
- uint8_t *source;
- int inputPitch;
- if (params.pack.reverseRowOrder)
- {
- source = static_cast<uint8_t*>(mapping.pData) + mapping.RowPitch * (params.area.height - 1);
- inputPitch = -static_cast<int>(mapping.RowPitch);
- }
- else
- {
- source = static_cast<uint8_t*>(mapping.pData);
- inputPitch = static_cast<int>(mapping.RowPitch);
+ return gl::OutOfMemory() << "Failed to map internal texture for reading, " << gl::FmtHR(hr);
}
- const d3d11::DXGIFormat &dxgiFormatInfo = d3d11::GetDXGIFormatInfo(textureHelper.getFormat());
- const gl::InternalFormat &sourceFormatInfo = gl::GetInternalFormatInfo(dxgiFormatInfo.internalFormat);
- if (sourceFormatInfo.format == params.format && sourceFormatInfo.type == params.type)
- {
- uint8_t *dest = pixelsOut + params.offset;
- for (int y = 0; y < params.area.height; y++)
- {
- memcpy(dest + y * params.outputPitch, source + y * inputPitch, params.area.width * sourceFormatInfo.pixelBytes);
- }
- }
- else
- {
- ColorCopyFunction fastCopyFunc =
- dxgiFormatInfo.getFastCopyFunction(params.format, params.type);
- GLenum sizedDestInternalFormat = gl::GetSizedInternalFormat(params.format, params.type);
- const gl::InternalFormat &destFormatInfo = gl::GetInternalFormatInfo(sizedDestInternalFormat);
-
- if (fastCopyFunc)
- {
- // Fast copy is possible through some special function
- for (int y = 0; y < params.area.height; y++)
- {
- for (int x = 0; x < params.area.width; x++)
- {
- uint8_t *dest = pixelsOut + params.offset + y * params.outputPitch + x * destFormatInfo.pixelBytes;
- const uint8_t *src = source + y * inputPitch + x * sourceFormatInfo.pixelBytes;
-
- fastCopyFunc(src, dest);
- }
- }
- }
- else
- {
- ColorReadFunction colorReadFunction = dxgiFormatInfo.colorReadFunction;
- ColorWriteFunction colorWriteFunction = GetColorWriteFunction(params.format, params.type);
-
- uint8_t temp[16]; // Maximum size of any Color<T> type used.
- static_assert(sizeof(temp) >= sizeof(gl::ColorF) &&
- sizeof(temp) >= sizeof(gl::ColorUI) &&
- sizeof(temp) >= sizeof(gl::ColorI),
- "Unexpected size of gl::Color struct.");
+ uint8_t *source = static_cast<uint8_t *>(mapping.pData);
+ int inputPitch = static_cast<int>(mapping.RowPitch);
- for (int y = 0; y < params.area.height; y++)
- {
- for (int x = 0; x < params.area.width; x++)
- {
- uint8_t *dest = pixelsOut + params.offset + y * params.outputPitch + x * destFormatInfo.pixelBytes;
- const uint8_t *src = source + y * inputPitch + x * sourceFormatInfo.pixelBytes;
+ const auto &formatInfo = textureHelper.getFormatSet();
+ ASSERT(formatInfo.format().glInternalFormat != GL_NONE);
- // readFunc and writeFunc will be using the same type of color, CopyTexImage
- // will not allow the copy otherwise.
- colorReadFunction(src, temp);
- colorWriteFunction(temp, dest);
- }
- }
- }
- }
+ PackPixels(params, formatInfo.format(), inputPitch, source, pixelsOut);
mDeviceContext->Unmap(readResource, 0);
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error Renderer11::blitRenderbufferRect(const gl::Rectangle &readRectIn,
+gl::Error Renderer11::blitRenderbufferRect(const gl::Context *context,
+ const gl::Rectangle &readRectIn,
const gl::Rectangle &drawRectIn,
RenderTargetD3D *readRenderTarget,
RenderTargetD3D *drawRenderTarget,
@@ -3735,63 +3371,64 @@ gl::Error Renderer11::blitRenderbufferRect(const gl::Rectangle &readRectIn,
ASSERT(colorBlit != (depthBlit || stencilBlit));
RenderTarget11 *drawRenderTarget11 = GetAs<RenderTarget11>(drawRenderTarget);
- if (!drawRenderTarget)
+ if (!drawRenderTarget11)
{
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to retrieve the internal draw render target from the draw framebuffer.");
+ return gl::OutOfMemory()
+ << "Failed to retrieve the internal draw render target from the draw framebuffer.";
}
- ID3D11Resource *drawTexture = drawRenderTarget11->getTexture();
- unsigned int drawSubresource = drawRenderTarget11->getSubresourceIndex();
- ID3D11RenderTargetView *drawRTV = drawRenderTarget11->getRenderTargetView();
- ID3D11DepthStencilView *drawDSV = drawRenderTarget11->getDepthStencilView();
+ const TextureHelper11 &drawTexture = drawRenderTarget11->getTexture();
+ unsigned int drawSubresource = drawRenderTarget11->getSubresourceIndex();
RenderTarget11 *readRenderTarget11 = GetAs<RenderTarget11>(readRenderTarget);
- if (!readRenderTarget)
+ if (!readRenderTarget11)
{
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to retrieve the internal read render target from the read framebuffer.");
+ return gl::OutOfMemory()
+ << "Failed to retrieve the internal read render target from the read framebuffer.";
}
- ID3D11Resource *readTexture = NULL;
- ID3D11ShaderResourceView *readSRV = NULL;
- unsigned int readSubresource = 0;
- if (readRenderTarget->getSamples() > 0)
+ TextureHelper11 readTexture;
+ unsigned int readSubresource = 0;
+ d3d11::SharedSRV readSRV;
+
+ if (readRenderTarget->isMultisampled())
{
- ID3D11Resource *unresolvedResource = readRenderTarget11->getTexture();
- ID3D11Texture2D *unresolvedTexture = d3d11::DynamicCastComObject<ID3D11Texture2D>(unresolvedResource);
+ ANGLE_TRY_RESULT(
+ resolveMultisampledTexture(context, readRenderTarget11, depthBlit, stencilBlit),
+ readTexture);
- if (unresolvedTexture)
+ if (!stencilBlit)
{
- readTexture = resolveMultisampledTexture(unresolvedTexture, readRenderTarget11->getSubresourceIndex());
- readSubresource = 0;
+ const auto &readFormatSet = readTexture.getFormatSet();
- SafeRelease(unresolvedTexture);
+ D3D11_SHADER_RESOURCE_VIEW_DESC viewDesc;
+ viewDesc.Format = readFormatSet.srvFormat;
+ viewDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2D;
+ viewDesc.Texture2D.MipLevels = 1;
+ viewDesc.Texture2D.MostDetailedMip = 0;
- HRESULT hresult = mDevice->CreateShaderResourceView(readTexture, NULL, &readSRV);
- if (FAILED(hresult))
- {
- SafeRelease(readTexture);
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create shader resource view to resolve multisampled framebuffer.");
- }
+ ANGLE_TRY(allocateResource(viewDesc, readTexture.get(), &readSRV));
}
}
else
{
- readTexture = readRenderTarget11->getTexture();
- readTexture->AddRef();
+ ASSERT(readRenderTarget11);
+ readTexture = readRenderTarget11->getTexture();
readSubresource = readRenderTarget11->getSubresourceIndex();
- readSRV = readRenderTarget11->getShaderResourceView();
- readSRV->AddRef();
+ readSRV = readRenderTarget11->getBlitShaderResourceView().makeCopy();
+ if (!readSRV.valid())
+ {
+ ASSERT(depthBlit || stencilBlit);
+ readSRV = readRenderTarget11->getShaderResourceView().makeCopy();
+ }
+ ASSERT(readSRV.valid());
}
- if (!readTexture || !readSRV)
- {
- SafeRelease(readTexture);
- SafeRelease(readSRV);
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to retrieve the internal read render target view from the read render target.");
- }
+ // Stencil blits don't use shaders.
+ ASSERT(readSRV.valid() || stencilBlit);
- gl::Extents readSize(readRenderTarget->getWidth(), readRenderTarget->getHeight(), 1);
- gl::Extents drawSize(drawRenderTarget->getWidth(), drawRenderTarget->getHeight(), 1);
+ const gl::Extents readSize(readRenderTarget->getWidth(), readRenderTarget->getHeight(), 1);
+ const gl::Extents drawSize(drawRenderTarget->getWidth(), drawRenderTarget->getHeight(), 1);
// From the spec:
// "The actual region taken from the read framebuffer is limited to the intersection of the
@@ -3801,8 +3438,32 @@ gl::Error Renderer11::blitRenderbufferRect(const gl::Rectangle &readRectIn,
// by internally scaling the read and draw rectangles.
gl::Rectangle readRect = readRectIn;
gl::Rectangle drawRect = drawRectIn;
- auto readToDrawX = [&drawRectIn, &readRectIn](int readOffset)
+
+ auto flip = [](int val) { return val >= 0 ? 1 : -1; };
+
+ if (readRect.x > readSize.width && readRect.width < 0)
+ {
+ int delta = readRect.x - readSize.width;
+ readRect.x -= delta;
+ readRect.width += delta;
+
+ int drawDelta = delta * flip(drawRect.width);
+ drawRect.x += drawDelta;
+ drawRect.width -= drawDelta;
+ }
+
+ if (readRect.y > readSize.height && readRect.height < 0)
{
+ int delta = readRect.y - readSize.height;
+ readRect.y -= delta;
+ readRect.height += delta;
+
+ int drawDelta = delta * flip(drawRect.height);
+ drawRect.y += drawDelta;
+ drawRect.height -= drawDelta;
+ }
+
+ auto readToDrawX = [&drawRectIn, &readRectIn](int readOffset) {
double readToDrawScale =
static_cast<double>(drawRectIn.width) / static_cast<double>(readRectIn.width);
return static_cast<int>(round(static_cast<double>(readOffset) * readToDrawScale));
@@ -3818,8 +3479,7 @@ gl::Error Renderer11::blitRenderbufferRect(const gl::Rectangle &readRectIn,
drawRect.width -= drawOffset;
}
- auto readToDrawY = [&drawRectIn, &readRectIn](int readOffset)
- {
+ auto readToDrawY = [&drawRectIn, &readRectIn](int readOffset) {
double readToDrawScale =
static_cast<double>(drawRectIn.height) / static_cast<double>(readRectIn.height);
return static_cast<int>(round(static_cast<double>(readOffset) * readToDrawScale));
@@ -3853,24 +3513,41 @@ gl::Error Renderer11::blitRenderbufferRect(const gl::Rectangle &readRectIn,
drawRect.height += drawOffset;
}
- bool scissorNeeded = scissor && gl::ClipRectangle(drawRect, *scissor, NULL);
+ if (readRect.x1() > readSize.width)
+ {
+ int delta = readRect.x1() - readSize.width;
+ readRect.width -= delta;
+ drawRect.width -= delta * flip(drawRect.width);
+ }
+
+ if (readRect.y1() > readSize.height)
+ {
+ int delta = readRect.y1() - readSize.height;
+ readRect.height -= delta;
+ drawRect.height -= delta * flip(drawRect.height);
+ }
+
+ bool scissorNeeded = scissor && gl::ClipRectangle(drawRect, *scissor, nullptr);
- const auto &destFormatInfo = gl::GetInternalFormatInfo(drawRenderTarget->getInternalFormat());
- const auto &srcFormatInfo = gl::GetInternalFormatInfo(readRenderTarget->getInternalFormat());
- const auto &dxgiFormatInfo = d3d11::GetDXGIFormatInfo(drawRenderTarget11->getDXGIFormat());
+ const auto &destFormatInfo =
+ gl::GetSizedInternalFormatInfo(drawRenderTarget->getInternalFormat());
+ const auto &srcFormatInfo =
+ gl::GetSizedInternalFormatInfo(readRenderTarget->getInternalFormat());
+ const auto &formatSet = drawRenderTarget11->getFormatSet();
+ const auto &nativeFormat = formatSet.format();
// Some blits require masking off emulated texture channels. eg: from RGBA8 to RGB8, we
// emulate RGB8 with RGBA8, so we need to mask off the alpha channel when we copy.
gl::Color<bool> colorMask;
- colorMask.red = (srcFormatInfo.redBits > 0) && (destFormatInfo.redBits == 0) &&
- (dxgiFormatInfo.redBits > 0);
+ colorMask.red =
+ (srcFormatInfo.redBits > 0) && (destFormatInfo.redBits == 0) && (nativeFormat.redBits > 0);
colorMask.green = (srcFormatInfo.greenBits > 0) && (destFormatInfo.greenBits == 0) &&
- (dxgiFormatInfo.greenBits > 0);
+ (nativeFormat.greenBits > 0);
colorMask.blue = (srcFormatInfo.blueBits > 0) && (destFormatInfo.blueBits == 0) &&
- (dxgiFormatInfo.blueBits > 0);
+ (nativeFormat.blueBits > 0);
colorMask.alpha = (srcFormatInfo.alphaBits > 0) && (destFormatInfo.alphaBits == 0) &&
- (dxgiFormatInfo.alphaBits > 0);
+ (nativeFormat.alphaBits > 0);
// We only currently support masking off the alpha channel.
bool colorMaskingNeeded = colorMask.alpha;
@@ -3884,18 +3561,19 @@ gl::Error Renderer11::blitRenderbufferRect(const gl::Rectangle &readRectIn,
bool stretchRequired = readRect.width != drawRect.width || readRect.height != drawRect.height;
- bool flipRequired = readRect.width < 0 || readRect.height < 0 || drawRect.width < 0 || drawRect.height < 0;
+ bool flipRequired =
+ readRect.width < 0 || readRect.height < 0 || drawRect.width < 0 || drawRect.height < 0;
bool outOfBounds = readRect.x < 0 || readRect.x + readRect.width > readSize.width ||
readRect.y < 0 || readRect.y + readRect.height > readSize.height ||
drawRect.x < 0 || drawRect.x + drawRect.width > drawSize.width ||
drawRect.y < 0 || drawRect.y + drawRect.height > drawSize.height;
- bool partialDSBlit = (dxgiFormatInfo.depthBits > 0 && depthBlit) != (dxgiFormatInfo.stencilBits > 0 && stencilBlit);
+ bool partialDSBlit =
+ (nativeFormat.depthBits > 0 && depthBlit) != (nativeFormat.stencilBits > 0 && stencilBlit);
- gl::Error result(GL_NO_ERROR);
-
- if (readRenderTarget11->getDXGIFormat() == drawRenderTarget11->getDXGIFormat() &&
+ if (readRenderTarget11->getFormatSet().formatID ==
+ drawRenderTarget11->getFormatSet().formatID &&
!stretchRequired && !outOfBounds && !flipRequired && !partialDSBlit &&
!colorMaskingNeeded && (!(depthBlit || stencilBlit) || wholeBufferCopy))
{
@@ -3903,16 +3581,17 @@ gl::Error Renderer11::blitRenderbufferRect(const gl::Rectangle &readRectIn,
UINT dstY = drawRect.y;
D3D11_BOX readBox;
- readBox.left = readRect.x;
- readBox.right = readRect.x + readRect.width;
- readBox.top = readRect.y;
+ readBox.left = readRect.x;
+ readBox.right = readRect.x + readRect.width;
+ readBox.top = readRect.y;
readBox.bottom = readRect.y + readRect.height;
- readBox.front = 0;
- readBox.back = 1;
+ readBox.front = 0;
+ readBox.back = 1;
if (scissorNeeded)
{
- // drawRect is guaranteed to have positive width and height because stretchRequired is false.
+ // drawRect is guaranteed to have positive width and height because stretchRequired is
+ // false.
ASSERT(drawRect.width >= 0 || drawRect.height >= 0);
if (drawRect.x < scissor->x)
@@ -3937,11 +3616,10 @@ gl::Error Renderer11::blitRenderbufferRect(const gl::Rectangle &readRectIn,
// D3D11 needs depth-stencil CopySubresourceRegions to have a NULL pSrcBox
// We also require complete framebuffer copies for depth-stencil blit.
- D3D11_BOX *pSrcBox = wholeBufferCopy ? NULL : &readBox;
+ D3D11_BOX *pSrcBox = wholeBufferCopy ? nullptr : &readBox;
- mDeviceContext->CopySubresourceRegion(drawTexture, drawSubresource, dstX, dstY, 0,
- readTexture, readSubresource, pSrcBox);
- result = gl::Error(GL_NO_ERROR);
+ mDeviceContext->CopySubresourceRegion(drawTexture.get(), drawSubresource, dstX, dstY, 0,
+ readTexture.get(), readSubresource, pSrcBox);
}
else
{
@@ -3950,47 +3628,56 @@ gl::Error Renderer11::blitRenderbufferRect(const gl::Rectangle &readRectIn,
if (depthBlit && stencilBlit)
{
- result = mBlit->copyDepthStencil(readTexture, readSubresource, readArea, readSize,
- drawTexture, drawSubresource, drawArea, drawSize,
- scissor);
+ ANGLE_TRY(mBlit->copyDepthStencil(readTexture, readSubresource, readArea, readSize,
+ drawTexture, drawSubresource, drawArea, drawSize,
+ scissor));
}
else if (depthBlit)
{
- result = mBlit->copyDepth(readSRV, readArea, readSize, drawDSV, drawArea, drawSize,
- scissor);
+ const d3d11::DepthStencilView &drawDSV = drawRenderTarget11->getDepthStencilView();
+ ASSERT(readSRV.valid());
+ ANGLE_TRY(mBlit->copyDepth(context, readSRV, readArea, readSize, drawDSV, drawArea,
+ drawSize, scissor));
}
else if (stencilBlit)
{
- result = mBlit->copyStencil(readTexture, readSubresource, readArea, readSize,
- drawTexture, drawSubresource, drawArea, drawSize,
- scissor);
+ ANGLE_TRY(mBlit->copyStencil(context, readTexture, readSubresource, readArea, readSize,
+ drawTexture, drawSubresource, drawArea, drawSize,
+ scissor));
}
else
{
+ const d3d11::RenderTargetView &drawRTV = drawRenderTarget11->getRenderTargetView();
+
// We don't currently support masking off any other channel than alpha
bool maskOffAlpha = colorMaskingNeeded && colorMask.alpha;
- result = mBlit->copyTexture(readSRV, readArea, readSize, drawRTV, drawArea, drawSize,
- scissor, destFormatInfo.format, filter, maskOffAlpha);
+ ASSERT(readSRV.valid());
+ ANGLE_TRY(mBlit->copyTexture(
+ context, readSRV, readArea, readSize, srcFormatInfo.format, drawRTV, drawArea,
+ drawSize, scissor, destFormatInfo.format, filter, maskOffAlpha, false, false));
}
}
- SafeRelease(readTexture);
- SafeRelease(readSRV);
-
- return result;
+ return gl::NoError();
}
bool Renderer11::isES3Capable() const
{
- return (d3d11_gl::GetMaximumClientVersion(mRenderer11DeviceCaps.featureLevel) > 2);
-};
+ return (d3d11_gl::GetMaximumClientVersion(mRenderer11DeviceCaps.featureLevel).major > 2);
+}
+
+RendererClass Renderer11::getRendererClass() const
+{
+ return RENDERER_D3D11;
+}
void Renderer11::onSwap()
{
// Send histogram updates every half hour
const double kHistogramUpdateInterval = 30 * 60;
- const double currentTime = ANGLEPlatformCurrent()->monotonicallyIncreasingTime();
+ auto *platform = ANGLEPlatformCurrent();
+ const double currentTime = platform->monotonicallyIncreasingTime(platform);
const double timeSinceLastUpdate = currentTime - mLastHistogramUpdateTime;
if (timeSinceLastUpdate > kHistogramUpdateInterval)
@@ -4005,7 +3692,7 @@ void Renderer11::updateHistograms()
// Update the buffer CPU memory histogram
{
size_t sizeSum = 0;
- for (auto &buffer : mAliveBuffers)
+ for (const Buffer11 *buffer : mAliveBuffers)
{
sizeSum += buffer->getTotalCPUBufferMemoryBytes();
}
@@ -4015,53 +3702,71 @@ void Renderer11::updateHistograms()
}
}
+void Renderer11::onBufferCreate(const Buffer11 *created)
+{
+ mAliveBuffers.insert(created);
+}
+
void Renderer11::onBufferDelete(const Buffer11 *deleted)
{
mAliveBuffers.erase(deleted);
}
-ID3D11Texture2D *Renderer11::resolveMultisampledTexture(ID3D11Texture2D *source, unsigned int subresource)
+gl::ErrorOrResult<TextureHelper11> Renderer11::resolveMultisampledTexture(
+ const gl::Context *context,
+ RenderTarget11 *renderTarget,
+ bool depth,
+ bool stencil)
{
- D3D11_TEXTURE2D_DESC textureDesc;
- source->GetDesc(&textureDesc);
+ if (depth && !stencil)
+ {
+ return mBlit->resolveDepth(context, renderTarget);
+ }
- if (textureDesc.SampleDesc.Count > 1)
+ if (stencil)
{
- D3D11_TEXTURE2D_DESC resolveDesc;
- resolveDesc.Width = textureDesc.Width;
- resolveDesc.Height = textureDesc.Height;
- resolveDesc.MipLevels = 1;
- resolveDesc.ArraySize = 1;
- resolveDesc.Format = textureDesc.Format;
- resolveDesc.SampleDesc.Count = 1;
- resolveDesc.SampleDesc.Quality = 0;
- resolveDesc.Usage = textureDesc.Usage;
- resolveDesc.BindFlags = textureDesc.BindFlags;
- resolveDesc.CPUAccessFlags = 0;
- resolveDesc.MiscFlags = 0;
+ return mBlit->resolveStencil(context, renderTarget, depth);
+ }
- ID3D11Texture2D *resolveTexture = NULL;
- HRESULT result = mDevice->CreateTexture2D(&resolveDesc, NULL, &resolveTexture);
- if (FAILED(result))
- {
- ERR("Failed to create a multisample resolve texture, HRESULT: 0x%X.", result);
- return NULL;
- }
+ const auto &formatSet = renderTarget->getFormatSet();
- mDeviceContext->ResolveSubresource(resolveTexture, 0, source, subresource, textureDesc.Format);
- return resolveTexture;
- }
- else
+ ASSERT(renderTarget->isMultisampled());
+ const d3d11::SharedSRV &sourceSRV = renderTarget->getShaderResourceView();
+ D3D11_SHADER_RESOURCE_VIEW_DESC sourceSRVDesc;
+ sourceSRV.get()->GetDesc(&sourceSRVDesc);
+ ASSERT(sourceSRVDesc.ViewDimension == D3D_SRV_DIMENSION_TEXTURE2DMS);
+
+ if (!mCachedResolveTexture.valid() ||
+ mCachedResolveTexture.getExtents().width != renderTarget->getWidth() ||
+ mCachedResolveTexture.getExtents().height != renderTarget->getHeight() ||
+ mCachedResolveTexture.getFormat() != formatSet.texFormat)
{
- source->AddRef();
- return source;
+ D3D11_TEXTURE2D_DESC resolveDesc;
+ resolveDesc.Width = renderTarget->getWidth();
+ resolveDesc.Height = renderTarget->getHeight();
+ resolveDesc.MipLevels = 1;
+ resolveDesc.ArraySize = 1;
+ resolveDesc.Format = formatSet.texFormat;
+ resolveDesc.SampleDesc.Count = 1;
+ resolveDesc.SampleDesc.Quality = 0;
+ resolveDesc.Usage = D3D11_USAGE_DEFAULT;
+ resolveDesc.BindFlags = D3D11_BIND_SHADER_RESOURCE;
+ resolveDesc.CPUAccessFlags = 0;
+ resolveDesc.MiscFlags = 0;
+
+ ANGLE_TRY(allocateTexture(resolveDesc, formatSet, &mCachedResolveTexture));
}
+
+ mDeviceContext->ResolveSubresource(mCachedResolveTexture.get(), 0,
+ renderTarget->getTexture().get(),
+ renderTarget->getSubresourceIndex(), formatSet.texFormat);
+ return mCachedResolveTexture;
}
bool Renderer11::getLUID(LUID *adapterLuid) const
{
adapterLuid->HighPart = 0;
- adapterLuid->LowPart = 0;
+ adapterLuid->LowPart = 0;
if (!mDxgiAdapter)
{
@@ -4078,45 +3783,70 @@ bool Renderer11::getLUID(LUID *adapterLuid) const
return true;
}
-VertexConversionType Renderer11::getVertexConversionType(gl::VertexFormatType vertexFormatType) const
+VertexConversionType Renderer11::getVertexConversionType(
+ gl::VertexFormatType vertexFormatType) const
{
- return d3d11::GetVertexFormatInfo(vertexFormatType, mRenderer11DeviceCaps.featureLevel).conversionType;
+ return d3d11::GetVertexFormatInfo(vertexFormatType, mRenderer11DeviceCaps.featureLevel)
+ .conversionType;
}
GLenum Renderer11::getVertexComponentType(gl::VertexFormatType vertexFormatType) const
{
- return d3d11::GetDXGIFormatInfo(d3d11::GetVertexFormatInfo(vertexFormatType, mRenderer11DeviceCaps.featureLevel).nativeFormat).componentType;
+ const auto &format =
+ d3d11::GetVertexFormatInfo(vertexFormatType, mRenderer11DeviceCaps.featureLevel);
+ return d3d11::GetComponentType(format.nativeFormat);
}
-void Renderer11::generateCaps(gl::Caps *outCaps, gl::TextureCapsMap *outTextureCaps,
- gl::Extensions *outExtensions, gl::Limitations *outLimitations) const
+gl::ErrorOrResult<unsigned int> Renderer11::getVertexSpaceRequired(
+ const gl::VertexAttribute &attrib,
+ const gl::VertexBinding &binding,
+ GLsizei count,
+ GLsizei instances) const
{
- d3d11_gl::GenerateCaps(mDevice, mDeviceContext, mRenderer11DeviceCaps, outCaps, outTextureCaps,
- outExtensions, outLimitations);
-}
+ if (!attrib.enabled)
+ {
+ return 16u;
+ }
-WorkaroundsD3D Renderer11::generateWorkarounds() const
-{
- return d3d11::GenerateWorkarounds(mRenderer11DeviceCaps.featureLevel);
+ unsigned int elementCount = 0;
+ const unsigned int divisor = binding.getDivisor();
+ if (instances == 0 || divisor == 0)
+ {
+ elementCount = count;
+ }
+ else
+ {
+ // Round up to divisor, if possible
+ elementCount = UnsignedCeilDivide(static_cast<unsigned int>(instances), divisor);
+ }
+
+ gl::VertexFormatType formatType = gl::GetVertexFormatType(attrib);
+ const D3D_FEATURE_LEVEL featureLevel = mRenderer11DeviceCaps.featureLevel;
+ const d3d11::VertexFormat &vertexFormatInfo =
+ d3d11::GetVertexFormatInfo(formatType, featureLevel);
+ const d3d11::DXGIFormatSize &dxgiFormatInfo =
+ d3d11::GetDXGIFormatSizeInfo(vertexFormatInfo.nativeFormat);
+ unsigned int elementSize = dxgiFormatInfo.pixelBytes;
+ if (elementSize > std::numeric_limits<unsigned int>::max() / elementCount)
+ {
+ return gl::OutOfMemory() << "New vertex buffer size would result in an overflow.";
+ }
+
+ return elementSize * elementCount;
}
-void Renderer11::createAnnotator()
+void Renderer11::generateCaps(gl::Caps *outCaps,
+ gl::TextureCapsMap *outTextureCaps,
+ gl::Extensions *outExtensions,
+ gl::Limitations *outLimitations) const
{
- // The D3D11 renderer must choose the D3D9 debug annotator because the D3D11 interface
- // method ID3DUserDefinedAnnotation::GetStatus on desktop builds doesn't work with the Graphics
- // Diagnostics tools in Visual Studio 2013.
- // The D3D9 annotator works properly for both D3D11 and D3D9.
- // Incorrect status reporting can cause ANGLE to log unnecessary debug events.
-#ifdef ANGLE_ENABLE_D3D9
- mAnnotator = new DebugAnnotator9();
-#else
- mAnnotator = new DebugAnnotator11();
-#endif
+ d3d11_gl::GenerateCaps(mDevice, mDeviceContext, mRenderer11DeviceCaps, outCaps, outTextureCaps,
+ outExtensions, outLimitations);
}
-gl::Error Renderer11::clearTextures(gl::SamplerType samplerType, size_t rangeStart, size_t rangeEnd)
+angle::WorkaroundsD3D Renderer11::generateWorkarounds() const
{
- return mStateManager.clearTextures(samplerType, rangeStart, rangeEnd);
+ return d3d11::GenerateWorkarounds(mRenderer11DeviceCaps, mAdapterDescription);
}
egl::Error Renderer11::getEGLDevice(DeviceImpl **device)
@@ -4136,6 +3866,224 @@ egl::Error Renderer11::getEGLDevice(DeviceImpl **device)
}
*device = static_cast<DeviceImpl *>(mEGLDevice);
- return egl::Error(EGL_SUCCESS);
+ return egl::NoError();
+}
+
+ContextImpl *Renderer11::createContext(const gl::ContextState &state)
+{
+ return new Context11(state, this);
+}
+
+FramebufferImpl *Renderer11::createDefaultFramebuffer(const gl::FramebufferState &state)
+{
+ return new Framebuffer11(state, this);
+}
+
+gl::Error Renderer11::getScratchMemoryBuffer(size_t requestedSize, angle::MemoryBuffer **bufferOut)
+{
+ if (!mScratchMemoryBuffer.get(requestedSize, bufferOut))
+ {
+ return gl::OutOfMemory() << "Failed to allocate internal buffer.";
+ }
+ return gl::NoError();
+}
+
+gl::Version Renderer11::getMaxSupportedESVersion() const
+{
+ return d3d11_gl::GetMaximumClientVersion(mRenderer11DeviceCaps.featureLevel);
+}
+
+gl::DebugAnnotator *Renderer11::getAnnotator()
+{
+ return mAnnotator;
+}
+
+gl::Error Renderer11::applyComputeShader(const gl::Context *context)
+{
+ ANGLE_TRY(ensureHLSLCompilerInitialized());
+
+ const auto &glState = context->getGLState();
+ ProgramD3D *programD3D = GetImplAs<ProgramD3D>(glState.getProgram());
+
+ ShaderExecutableD3D *computeExe = nullptr;
+ ANGLE_TRY(programD3D->getComputeExecutable(&computeExe));
+ ASSERT(computeExe != nullptr);
+
+ mStateManager.setComputeShader(&GetAs<ShaderExecutable11>(computeExe)->getComputeShader());
+ ANGLE_TRY(mStateManager.applyComputeUniforms(programD3D));
+
+ return gl::NoError();
+}
+
+gl::Error Renderer11::dispatchCompute(const gl::Context *context,
+ GLuint numGroupsX,
+ GLuint numGroupsY,
+ GLuint numGroupsZ)
+{
+ ANGLE_TRY(mStateManager.updateStateForCompute(context, numGroupsX, numGroupsY, numGroupsZ));
+ ANGLE_TRY(applyComputeShader(context));
+
+ mDeviceContext->Dispatch(numGroupsX, numGroupsY, numGroupsZ);
+
+ return gl::NoError();
+}
+
+gl::ErrorOrResult<TextureHelper11> Renderer11::createStagingTexture(
+ ResourceType textureType,
+ const d3d11::Format &formatSet,
+ const gl::Extents &size,
+ StagingAccess readAndWriteAccess)
+{
+ if (textureType == ResourceType::Texture2D)
+ {
+ D3D11_TEXTURE2D_DESC stagingDesc;
+ stagingDesc.Width = size.width;
+ stagingDesc.Height = size.height;
+ stagingDesc.MipLevels = 1;
+ stagingDesc.ArraySize = 1;
+ stagingDesc.Format = formatSet.texFormat;
+ stagingDesc.SampleDesc.Count = 1;
+ stagingDesc.SampleDesc.Quality = 0;
+ stagingDesc.Usage = D3D11_USAGE_STAGING;
+ stagingDesc.BindFlags = 0;
+ stagingDesc.CPUAccessFlags = D3D11_CPU_ACCESS_READ;
+ stagingDesc.MiscFlags = 0;
+
+ if (readAndWriteAccess == StagingAccess::READ_WRITE)
+ {
+ stagingDesc.CPUAccessFlags |= D3D11_CPU_ACCESS_WRITE;
+ }
+
+ TextureHelper11 stagingTex;
+ ANGLE_TRY(allocateTexture(stagingDesc, formatSet, &stagingTex));
+ return stagingTex;
+ }
+ ASSERT(textureType == ResourceType::Texture3D);
+
+ D3D11_TEXTURE3D_DESC stagingDesc;
+ stagingDesc.Width = size.width;
+ stagingDesc.Height = size.height;
+ stagingDesc.Depth = 1;
+ stagingDesc.MipLevels = 1;
+ stagingDesc.Format = formatSet.texFormat;
+ stagingDesc.Usage = D3D11_USAGE_STAGING;
+ stagingDesc.BindFlags = 0;
+ stagingDesc.CPUAccessFlags = D3D11_CPU_ACCESS_READ;
+ stagingDesc.MiscFlags = 0;
+
+ TextureHelper11 stagingTex;
+ ANGLE_TRY(allocateTexture(stagingDesc, formatSet, &stagingTex));
+ return stagingTex;
+}
+
+gl::Error Renderer11::allocateTexture(const D3D11_TEXTURE2D_DESC &desc,
+ const d3d11::Format &format,
+ const D3D11_SUBRESOURCE_DATA *initData,
+ TextureHelper11 *textureOut)
+{
+ d3d11::Texture2D texture;
+ ANGLE_TRY(mResourceManager11.allocate(this, &desc, initData, &texture));
+ textureOut->init(std::move(texture), desc, format);
+ return gl::NoError();
+}
+
+gl::Error Renderer11::allocateTexture(const D3D11_TEXTURE3D_DESC &desc,
+ const d3d11::Format &format,
+ const D3D11_SUBRESOURCE_DATA *initData,
+ TextureHelper11 *textureOut)
+{
+ d3d11::Texture3D texture;
+ ANGLE_TRY(mResourceManager11.allocate(this, &desc, initData, &texture));
+ textureOut->init(std::move(texture), desc, format);
+ return gl::NoError();
+}
+
+gl::Error Renderer11::getBlendState(const d3d11::BlendStateKey &key,
+ const d3d11::BlendState **outBlendState)
+{
+ return mStateCache.getBlendState(this, key, outBlendState);
+}
+
+gl::Error Renderer11::getRasterizerState(const gl::RasterizerState &rasterState,
+ bool scissorEnabled,
+ ID3D11RasterizerState **outRasterizerState)
+{
+ return mStateCache.getRasterizerState(this, rasterState, scissorEnabled, outRasterizerState);
+}
+
+gl::Error Renderer11::getDepthStencilState(const gl::DepthStencilState &dsState,
+ const d3d11::DepthStencilState **outDSState)
+{
+ return mStateCache.getDepthStencilState(this, dsState, outDSState);
+}
+
+gl::Error Renderer11::getSamplerState(const gl::SamplerState &samplerState,
+ ID3D11SamplerState **outSamplerState)
+{
+ return mStateCache.getSamplerState(this, samplerState, outSamplerState);
+}
+
+gl::Error Renderer11::clearRenderTarget(RenderTargetD3D *renderTarget,
+ const gl::ColorF &clearColorValue,
+ const float clearDepthValue,
+ const unsigned int clearStencilValue)
+{
+ RenderTarget11 *rt11 = GetAs<RenderTarget11>(renderTarget);
+
+ if (rt11->getDepthStencilView().valid())
+ {
+ const auto &format = rt11->getFormatSet();
+ const UINT clearFlags = (format.format().depthBits > 0 ? D3D11_CLEAR_DEPTH : 0) |
+ (format.format().stencilBits ? D3D11_CLEAR_STENCIL : 0);
+ mDeviceContext->ClearDepthStencilView(rt11->getDepthStencilView().get(), clearFlags,
+ clearDepthValue,
+ static_cast<UINT8>(clearStencilValue));
+ return gl::NoError();
+ }
+
+ ASSERT(rt11->getRenderTargetView().valid());
+ ID3D11RenderTargetView *rtv = rt11->getRenderTargetView().get();
+
+ // There are complications with some types of RTV and FL 9_3 with ClearRenderTargetView.
+ // See https://msdn.microsoft.com/en-us/library/windows/desktop/ff476388(v=vs.85).aspx
+ ASSERT(mRenderer11DeviceCaps.featureLevel > D3D_FEATURE_LEVEL_9_3 || !IsArrayRTV(rtv));
+
+ const auto &d3d11Format = rt11->getFormatSet();
+ const auto &glFormat = gl::GetSizedInternalFormatInfo(renderTarget->getInternalFormat());
+
+ gl::ColorF safeClearColor = clearColorValue;
+
+ if (d3d11Format.format().alphaBits > 0 && glFormat.alphaBits == 0)
+ {
+ safeClearColor.alpha = 1.0f;
+ }
+
+ mDeviceContext->ClearRenderTargetView(rtv, &safeClearColor.red);
+ return gl::NoError();
+}
+
+bool Renderer11::canSelectViewInVertexShader() const
+{
+ return !getWorkarounds().selectViewInGeometryShader &&
+ getRenderer11DeviceCaps().supportsVpRtIndexWriteFromVertexShader;
}
+
+gl::Error Renderer11::markTransformFeedbackUsage(const gl::Context *context)
+{
+ const gl::State &glState = context->getGLState();
+ const gl::TransformFeedback *transformFeedback = glState.getCurrentTransformFeedback();
+ for (size_t i = 0; i < transformFeedback->getIndexedBufferCount(); i++)
+ {
+ const gl::OffsetBindingPointer<gl::Buffer> &binding =
+ transformFeedback->getIndexedBuffer(i);
+ if (binding.get() != nullptr)
+ {
+ BufferD3D *bufferD3D = GetImplAs<BufferD3D>(binding.get());
+ ANGLE_TRY(bufferD3D->markTransformFeedbackUsage(context));
+ }
+ }
+
+ return gl::NoError();
}
+
+} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Renderer11.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Renderer11.h
index b4e7761ffc..a8c24e681b 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Renderer11.h
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Renderer11.h
@@ -14,13 +14,14 @@
#include "libANGLE/AttributeMap.h"
#include "libANGLE/angletypes.h"
#include "libANGLE/renderer/d3d/HLSLCompiler.h"
-#include "libANGLE/renderer/d3d/RendererD3D.h"
+#include "libANGLE/renderer/d3d/ProgramD3D.h"
#include "libANGLE/renderer/d3d/RenderTargetD3D.h"
+#include "libANGLE/renderer/d3d/RendererD3D.h"
#include "libANGLE/renderer/d3d/d3d11/DebugAnnotator11.h"
-#include "libANGLE/renderer/d3d/d3d11/InputLayoutCache.h"
-#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
#include "libANGLE/renderer/d3d/d3d11/RenderStateCache.h"
+#include "libANGLE/renderer/d3d/d3d11/ResourceManager11.h"
#include "libANGLE/renderer/d3d/d3d11/StateManager11.h"
+#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
namespace gl
{
@@ -28,36 +29,46 @@ class FramebufferAttachment;
struct ImageIndex;
}
-struct ID3D11DeviceContext1;
-
namespace rx
{
-
-class VertexDataManager;
-class IndexDataManager;
-class StreamingIndexBufferInterface;
class Blit11;
class Buffer11;
class Clear11;
+class Context11;
+class IndexDataManager;
+struct PackPixelsParams;
class PixelTransfer11;
class RenderTarget11;
+class StreamingIndexBufferInterface;
class Trim11;
-struct PackPixelsParams;
+class VertexDataManager;
struct Renderer11DeviceCaps
{
+ Renderer11DeviceCaps();
+
D3D_FEATURE_LEVEL featureLevel;
- bool supportsDXGI1_2; // Support for DXGI 1.2
- bool supportsClearView; // Support for ID3D11DeviceContext1::ClearView
- bool supportsConstantBufferOffsets; // Support for Constant buffer offset
- UINT B5G6R5support; // Bitfield of D3D11_FORMAT_SUPPORT values for DXGI_FORMAT_B5G6R5_UNORM
- UINT B4G4R4A4support; // Bitfield of D3D11_FORMAT_SUPPORT values for DXGI_FORMAT_B4G4R4A4_UNORM
- UINT B5G5R5A1support; // Bitfield of D3D11_FORMAT_SUPPORT values for DXGI_FORMAT_B5G5R5A1_UNORM
+ bool supportsDXGI1_2; // Support for DXGI 1.2
+ bool supportsClearView; // Support for ID3D11DeviceContext1::ClearView
+ bool supportsConstantBufferOffsets; // Support for Constant buffer offset
+ bool supportsVpRtIndexWriteFromVertexShader; // VP/RT can be selected in the Vertex Shader
+ // stage.
+ bool supportsMultisampledDepthStencilSRVs; // D3D feature level 10.0 no longer allows creation
+ // of textures with both the bind SRV and DSV flags
+ // when multisampled. Textures will need to be
+ // resolved before reading. crbug.com/656989
+ UINT B5G6R5support; // Bitfield of D3D11_FORMAT_SUPPORT values for DXGI_FORMAT_B5G6R5_UNORM
+ UINT B5G6R5maxSamples; // Maximum number of samples supported by DXGI_FORMAT_B5G6R5_UNORM
+ UINT B4G4R4A4support; // Bitfield of D3D11_FORMAT_SUPPORT values for DXGI_FORMAT_B4G4R4A4_UNORM
+ UINT B4G4R4A4maxSamples; // Maximum number of samples supported by DXGI_FORMAT_B4G4R4A4_UNORM
+ UINT B5G5R5A1support; // Bitfield of D3D11_FORMAT_SUPPORT values for DXGI_FORMAT_B5G5R5A1_UNORM
+ UINT B5G5R5A1maxSamples; // Maximum number of samples supported by DXGI_FORMAT_B5G5R5A1_UNORM
+ Optional<LARGE_INTEGER> driverVersion; // Four-part driver version number.
};
enum
{
- MAX_VERTEX_UNIFORM_VECTORS_D3D11 = 1024,
+ MAX_VERTEX_UNIFORM_VECTORS_D3D11 = 1024,
MAX_FRAGMENT_UNIFORM_VECTORS_D3D11 = 1024
};
@@ -103,172 +114,244 @@ class Renderer11 : public RendererD3D
{
public:
explicit Renderer11(egl::Display *display);
- virtual ~Renderer11();
+ ~Renderer11() override;
egl::Error initialize() override;
- virtual bool resetDevice();
+ bool resetDevice() override;
- egl::ConfigSet generateConfigs() const override;
+ egl::ConfigSet generateConfigs() override;
void generateDisplayExtensions(egl::DisplayExtensions *outExtensions) const override;
- gl::Error flush() override;
- gl::Error finish() override;
+ ContextImpl *createContext(const gl::ContextState &state) override;
+
+ gl::Error flush();
+ gl::Error finish();
- SwapChainD3D *createSwapChain(NativeWindow nativeWindow,
+ bool isValidNativeWindow(EGLNativeWindowType window) const override;
+ NativeWindowD3D *createNativeWindow(EGLNativeWindowType window,
+ const egl::Config *config,
+ const egl::AttributeMap &attribs) const override;
+
+ SwapChainD3D *createSwapChain(NativeWindowD3D *nativeWindow,
HANDLE shareHandle,
+ IUnknown *d3dTexture,
GLenum backBufferFormat,
GLenum depthBufferFormat,
- EGLint orientation) override;
-
- CompilerImpl *createCompiler() override;
-
- virtual gl::Error generateSwizzle(gl::Texture *texture);
- virtual gl::Error setSamplerState(gl::SamplerType type, int index, gl::Texture *texture, const gl::SamplerState &sampler);
- virtual gl::Error setTexture(gl::SamplerType type, int index, gl::Texture *texture);
-
- gl::Error setUniformBuffers(const gl::Data &data,
- const std::vector<GLint> &vertexUniformBuffers,
- const std::vector<GLint> &fragmentUniformBuffers) override;
-
- gl::Error updateState(const gl::Data &data, GLenum drawMode) override;
-
- virtual bool applyPrimitiveType(GLenum mode, GLsizei count, bool usesPointSize);
- gl::Error applyRenderTarget(const gl::Framebuffer *frameBuffer) override;
- gl::Error applyUniforms(const ProgramD3D &programD3D,
- GLenum drawMode,
- const std::vector<D3DUniform *> &uniformArray) override;
- virtual gl::Error applyVertexBuffer(const gl::State &state,
- GLenum mode,
- GLint first,
- GLsizei count,
- GLsizei instances,
- TranslatedIndexData *indexInfo);
- gl::Error applyIndexBuffer(const gl::Data &data,
- const GLvoid *indices,
- GLsizei count,
- GLenum mode,
- GLenum type,
- TranslatedIndexData *indexInfo) override;
- void applyTransformFeedbackBuffers(const gl::State &state) override;
+ EGLint orientation,
+ EGLint samples) override;
+ egl::Error getD3DTextureInfo(const egl::Config *configuration,
+ IUnknown *d3dTexture,
+ EGLint *width,
+ EGLint *height,
+ GLenum *fboFormat) const override;
+ egl::Error validateShareHandle(const egl::Config *config,
+ HANDLE shareHandle,
+ const egl::AttributeMap &attribs) const override;
+
+ bool applyPrimitiveType(const gl::State &glState, GLenum mode, GLsizei count);
// lost device
bool testDeviceLost() override;
bool testDeviceResettable() override;
- std::string getRendererDescription() const override;
+ std::string getRendererDescription() const;
DeviceIdentifier getAdapterIdentifier() const override;
- virtual unsigned int getReservedVertexUniformVectors() const;
- virtual unsigned int getReservedFragmentUniformVectors() const;
- virtual unsigned int getReservedVertexUniformBuffers() const;
- virtual unsigned int getReservedFragmentUniformBuffers() const;
+ unsigned int getReservedVertexUniformVectors() const;
+ unsigned int getReservedFragmentUniformVectors() const;
+ unsigned int getReservedVertexUniformBuffers() const;
+ unsigned int getReservedFragmentUniformBuffers() const;
bool getShareHandleSupport() const;
- virtual int getMajorShaderModel() const;
+ bool getNV12TextureSupport() const;
+
+ int getMajorShaderModel() const override;
int getMinorShaderModel() const override;
std::string getShaderModelSuffix() const override;
// Pixel operations
- virtual gl::Error copyImage2D(const gl::Framebuffer *framebuffer, const gl::Rectangle &sourceRect, GLenum destFormat,
- const gl::Offset &destOffset, TextureStorage *storage, GLint level);
- virtual gl::Error copyImageCube(const gl::Framebuffer *framebuffer, const gl::Rectangle &sourceRect, GLenum destFormat,
- const gl::Offset &destOffset, TextureStorage *storage, GLenum target, GLint level);
- virtual gl::Error copyImage3D(const gl::Framebuffer *framebuffer, const gl::Rectangle &sourceRect, GLenum destFormat,
- const gl::Offset &destOffset, TextureStorage *storage, GLint level);
- virtual gl::Error copyImage2DArray(const gl::Framebuffer *framebuffer, const gl::Rectangle &sourceRect, GLenum destFormat,
- const gl::Offset &destOffset, TextureStorage *storage, GLint level);
+ gl::Error copyImage2D(const gl::Context *context,
+ const gl::Framebuffer *framebuffer,
+ const gl::Rectangle &sourceRect,
+ GLenum destFormat,
+ const gl::Offset &destOffset,
+ TextureStorage *storage,
+ GLint level) override;
+ gl::Error copyImageCube(const gl::Context *context,
+ const gl::Framebuffer *framebuffer,
+ const gl::Rectangle &sourceRect,
+ GLenum destFormat,
+ const gl::Offset &destOffset,
+ TextureStorage *storage,
+ GLenum target,
+ GLint level) override;
+ gl::Error copyImage3D(const gl::Context *context,
+ const gl::Framebuffer *framebuffer,
+ const gl::Rectangle &sourceRect,
+ GLenum destFormat,
+ const gl::Offset &destOffset,
+ TextureStorage *storage,
+ GLint level) override;
+ gl::Error copyImage2DArray(const gl::Context *context,
+ const gl::Framebuffer *framebuffer,
+ const gl::Rectangle &sourceRect,
+ GLenum destFormat,
+ const gl::Offset &destOffset,
+ TextureStorage *storage,
+ GLint level) override;
+
+ gl::Error copyTexture(const gl::Context *context,
+ const gl::Texture *source,
+ GLint sourceLevel,
+ const gl::Rectangle &sourceRect,
+ GLenum destFormat,
+ const gl::Offset &destOffset,
+ TextureStorage *storage,
+ GLenum destTarget,
+ GLint destLevel,
+ bool unpackFlipY,
+ bool unpackPremultiplyAlpha,
+ bool unpackUnmultiplyAlpha) override;
+ gl::Error copyCompressedTexture(const gl::Context *context,
+ const gl::Texture *source,
+ GLint sourceLevel,
+ TextureStorage *storage,
+ GLint destLevel) override;
// RenderTarget creation
- virtual gl::Error createRenderTarget(int width, int height, GLenum format, GLsizei samples, RenderTargetD3D **outRT);
+ gl::Error createRenderTarget(int width,
+ int height,
+ GLenum format,
+ GLsizei samples,
+ RenderTargetD3D **outRT) override;
gl::Error createRenderTargetCopy(RenderTargetD3D *source, RenderTargetD3D **outRT) override;
- // Framebuffer creation
- FramebufferImpl *createFramebuffer(const gl::Framebuffer::Data &data) override;
-
- // Shader creation
- ShaderImpl *createShader(const gl::Shader::Data &data) override;
- ProgramImpl *createProgram(const gl::Program::Data &data) override;
-
// Shader operations
- gl::Error loadExecutable(const void *function,
+ gl::Error loadExecutable(const uint8_t *function,
size_t length,
- ShaderType type,
+ gl::ShaderType type,
const std::vector<D3DVarying> &streamOutVaryings,
bool separatedOutputBuffers,
ShaderExecutableD3D **outExecutable) override;
gl::Error compileToExecutable(gl::InfoLog &infoLog,
const std::string &shaderHLSL,
- ShaderType type,
+ gl::ShaderType type,
const std::vector<D3DVarying> &streamOutVaryings,
bool separatedOutputBuffers,
- const D3DCompilerWorkarounds &workarounds,
+ const angle::CompilerWorkaroundsD3D &workarounds,
ShaderExecutableD3D **outExectuable) override;
+ gl::Error ensureHLSLCompilerInitialized() override;
+
UniformStorageD3D *createUniformStorage(size_t storageSize) override;
// Image operations
- virtual ImageD3D *createImage();
- gl::Error generateMipmap(ImageD3D *dest, ImageD3D *source) override;
- gl::Error generateMipmapsUsingD3D(TextureStorage *storage,
- const gl::TextureState &textureState) override;
- virtual TextureStorage *createTextureStorage2D(SwapChainD3D *swapChain);
- TextureStorage *createTextureStorageEGLImage(EGLImageD3D *eglImage) override;
- virtual TextureStorage *createTextureStorage2D(GLenum internalformat, bool renderTarget, GLsizei width, GLsizei height, int levels, bool hintLevelZeroOnly);
- virtual TextureStorage *createTextureStorageCube(GLenum internalformat, bool renderTarget, int size, int levels, bool hintLevelZeroOnly);
- virtual TextureStorage *createTextureStorage3D(GLenum internalformat, bool renderTarget, GLsizei width, GLsizei height, GLsizei depth, int levels);
- virtual TextureStorage *createTextureStorage2DArray(GLenum internalformat, bool renderTarget, GLsizei width, GLsizei height, GLsizei depth, int levels);
-
- // Texture creation
- virtual TextureImpl *createTexture(GLenum target);
-
- // Renderbuffer creation
- virtual RenderbufferImpl *createRenderbuffer();
-
- // Buffer creation
- virtual BufferImpl *createBuffer();
- virtual VertexBuffer *createVertexBuffer();
- virtual IndexBuffer *createIndexBuffer();
-
- // Vertex Array creation
- VertexArrayImpl *createVertexArray(const gl::VertexArray::Data &data) override;
-
- // Query and Fence creation
- virtual QueryImpl *createQuery(GLenum type);
- virtual FenceNVImpl *createFenceNV();
- virtual FenceSyncImpl *createFenceSync();
-
- // Transform Feedback creation
- virtual TransformFeedbackImpl* createTransformFeedback();
+ ImageD3D *createImage() override;
+ gl::Error generateMipmap(const gl::Context *context, ImageD3D *dest, ImageD3D *source) override;
+ gl::Error generateMipmapUsingD3D(const gl::Context *context,
+ TextureStorage *storage,
+ const gl::TextureState &textureState) override;
+ gl::Error copyImage(const gl::Context *context,
+ ImageD3D *dest,
+ ImageD3D *source,
+ const gl::Rectangle &sourceRect,
+ const gl::Offset &destOffset,
+ bool unpackFlipY,
+ bool unpackPremultiplyAlpha,
+ bool unpackUnmultiplyAlpha) override;
+ TextureStorage *createTextureStorage2D(SwapChainD3D *swapChain) override;
+ TextureStorage *createTextureStorageEGLImage(EGLImageD3D *eglImage,
+ RenderTargetD3D *renderTargetD3D) override;
+ TextureStorage *createTextureStorageExternal(
+ egl::Stream *stream,
+ const egl::Stream::GLTextureDescription &desc) override;
+ TextureStorage *createTextureStorage2D(GLenum internalformat,
+ bool renderTarget,
+ GLsizei width,
+ GLsizei height,
+ int levels,
+ bool hintLevelZeroOnly) override;
+ TextureStorage *createTextureStorageCube(GLenum internalformat,
+ bool renderTarget,
+ int size,
+ int levels,
+ bool hintLevelZeroOnly) override;
+ TextureStorage *createTextureStorage3D(GLenum internalformat,
+ bool renderTarget,
+ GLsizei width,
+ GLsizei height,
+ GLsizei depth,
+ int levels) override;
+ TextureStorage *createTextureStorage2DArray(GLenum internalformat,
+ bool renderTarget,
+ GLsizei width,
+ GLsizei height,
+ GLsizei depth,
+ int levels) override;
+ TextureStorage *createTextureStorage2DMultisample(GLenum internalformat,
+ GLsizei width,
+ GLsizei height,
+ int levels,
+ int samples,
+ bool fixedSampleLocations) override;
+
+ VertexBuffer *createVertexBuffer() override;
+ IndexBuffer *createIndexBuffer() override;
+
+ // Stream Creation
+ StreamProducerImpl *createStreamProducerD3DTextureNV12(
+ egl::Stream::ConsumerType consumerType,
+ const egl::AttributeMap &attribs) override;
// D3D11-renderer specific methods
ID3D11Device *getDevice() { return mDevice; }
void *getD3DDevice() override;
ID3D11DeviceContext *getDeviceContext() { return mDeviceContext; };
ID3D11DeviceContext1 *getDeviceContext1IfSupported() { return mDeviceContext1; };
- DXGIFactory *getDxgiFactory() { return mDxgiFactory; };
-
- RenderStateCache &getStateCache() { return mStateCache; }
+ IDXGIFactory *getDxgiFactory() { return mDxgiFactory; };
+
+ gl::Error getBlendState(const d3d11::BlendStateKey &key,
+ const d3d11::BlendState **outBlendState);
+ gl::Error getRasterizerState(const gl::RasterizerState &rasterState,
+ bool scissorEnabled,
+ ID3D11RasterizerState **outRasterizerState);
+ gl::Error getDepthStencilState(const gl::DepthStencilState &dsState,
+ const d3d11::DepthStencilState **outDSState);
+ gl::Error getSamplerState(const gl::SamplerState &samplerState,
+ ID3D11SamplerState **outSamplerState);
Blit11 *getBlitter() { return mBlit; }
Clear11 *getClearer() { return mClear; }
+ gl::DebugAnnotator *getAnnotator();
// Buffer-to-texture and Texture-to-buffer copies
- virtual bool supportsFastCopyBufferToTexture(GLenum internalFormat) const;
- virtual gl::Error fastCopyBufferToTexture(const gl::PixelUnpackState &unpack, unsigned int offset, RenderTargetD3D *destRenderTarget,
- GLenum destinationFormat, GLenum sourcePixelsType, const gl::Box &destArea);
+ bool supportsFastCopyBufferToTexture(GLenum internalFormat) const override;
+ gl::Error fastCopyBufferToTexture(const gl::Context *context,
+ const gl::PixelUnpackState &unpack,
+ unsigned int offset,
+ RenderTargetD3D *destRenderTarget,
+ GLenum destinationFormat,
+ GLenum sourcePixelsType,
+ const gl::Box &destArea) override;
- void markAllStateDirty();
- void unapplyRenderTargets();
- void setOneTimeRenderTarget(ID3D11RenderTargetView *renderTargetView);
gl::Error packPixels(const TextureHelper11 &textureHelper,
const PackPixelsParams &params,
uint8_t *pixelsOut);
bool getLUID(LUID *adapterLuid) const override;
- VertexConversionType getVertexConversionType(gl::VertexFormatType vertexFormatType) const override;
+ VertexConversionType getVertexConversionType(
+ gl::VertexFormatType vertexFormatType) const override;
GLenum getVertexComponentType(gl::VertexFormatType vertexFormatType) const override;
- gl::Error readFromAttachment(const gl::FramebufferAttachment &srcAttachment,
+ // Warning: you should ensure binding really matches attrib.bindingIndex before using this
+ // function.
+ gl::ErrorOrResult<unsigned int> getVertexSpaceRequired(const gl::VertexAttribute &attrib,
+ const gl::VertexBinding &binding,
+ GLsizei count,
+ GLsizei instances) const override;
+
+ gl::Error readFromAttachment(const gl::Context *context,
+ const gl::FramebufferAttachment &srcAttachment,
const gl::Rectangle &sourceArea,
GLenum format,
GLenum type,
@@ -276,145 +359,175 @@ class Renderer11 : public RendererD3D
const gl::PixelPackState &pack,
uint8_t *pixels);
- gl::Error blitRenderbufferRect(const gl::Rectangle &readRect, const gl::Rectangle &drawRect, RenderTargetD3D *readRenderTarget,
- RenderTargetD3D *drawRenderTarget, GLenum filter, const gl::Rectangle *scissor,
- bool colorBlit, bool depthBlit, bool stencilBlit);
+ gl::Error blitRenderbufferRect(const gl::Context *context,
+ const gl::Rectangle &readRect,
+ const gl::Rectangle &drawRect,
+ RenderTargetD3D *readRenderTarget,
+ RenderTargetD3D *drawRenderTarget,
+ GLenum filter,
+ const gl::Rectangle *scissor,
+ bool colorBlit,
+ bool depthBlit,
+ bool stencilBlit);
bool isES3Capable() const;
- const Renderer11DeviceCaps &getRenderer11DeviceCaps() { return mRenderer11DeviceCaps; };
+ const Renderer11DeviceCaps &getRenderer11DeviceCaps() const { return mRenderer11DeviceCaps; };
- RendererClass getRendererClass() const override { return RENDERER_D3D11; }
- InputLayoutCache *getInputLayoutCache() { return &mInputLayoutCache; }
+ RendererClass getRendererClass() const override;
StateManager11 *getStateManager() { return &mStateManager; }
void onSwap();
+ void onBufferCreate(const Buffer11 *created);
void onBufferDelete(const Buffer11 *deleted);
egl::Error getEGLDevice(DeviceImpl **device) override;
- protected:
- void createAnnotator() override;
- gl::Error clearTextures(gl::SamplerType samplerType, size_t rangeStart, size_t rangeEnd) override;
- gl::Error applyShadersImpl(const gl::Data &data, GLenum drawMode) override;
+ gl::Error drawArrays(const gl::Context *context,
+ GLenum mode,
+ GLint startVertex,
+ GLsizei count,
+ GLsizei instances);
- void syncState(const gl::State &state, const gl::State::DirtyBits &bitmask) override;
+ gl::Error drawElements(const gl::Context *context,
+ GLenum mode,
+ GLsizei count,
+ GLenum type,
+ const void *indices,
+ GLsizei instances);
+
+ gl::Error drawArraysIndirect(const gl::Context *context, GLenum mode, const void *indirect);
+ gl::Error drawElementsIndirect(const gl::Context *context,
+ GLenum mode,
+ GLenum type,
+ const void *indirect);
+
+ // Necessary hack for default framebuffers in D3D.
+ FramebufferImpl *createDefaultFramebuffer(const gl::FramebufferState &state) override;
+
+ gl::Error getScratchMemoryBuffer(size_t requestedSize, angle::MemoryBuffer **bufferOut);
+
+ gl::Version getMaxSupportedESVersion() const override;
+
+ gl::Error dispatchCompute(const gl::Context *context,
+ GLuint numGroupsX,
+ GLuint numGroupsY,
+ GLuint numGroupsZ);
+ gl::Error applyComputeShader(const gl::Context *context);
+
+ gl::ErrorOrResult<TextureHelper11> createStagingTexture(ResourceType textureType,
+ const d3d11::Format &formatSet,
+ const gl::Extents &size,
+ StagingAccess readAndWriteAccess);
+
+ template <typename DescT, typename ResourceT>
+ gl::Error allocateResource(const DescT &desc, ResourceT *resourceOut)
+ {
+ return mResourceManager11.allocate(this, &desc, nullptr, resourceOut);
+ }
+
+ template <typename DescT, typename InitDataT, typename ResourceT>
+ gl::Error allocateResource(const DescT &desc, InitDataT *initData, ResourceT *resourceOut)
+ {
+ return mResourceManager11.allocate(this, &desc, initData, resourceOut);
+ }
+
+ template <typename InitDataT, typename ResourceT>
+ gl::Error allocateResourceNoDesc(InitDataT *initData, ResourceT *resourceOut)
+ {
+ return mResourceManager11.allocate(this, nullptr, initData, resourceOut);
+ }
+
+ template <typename DescT>
+ gl::Error allocateTexture(const DescT &desc,
+ const d3d11::Format &format,
+ TextureHelper11 *textureOut)
+ {
+ return allocateTexture(desc, format, nullptr, textureOut);
+ }
+
+ gl::Error allocateTexture(const D3D11_TEXTURE2D_DESC &desc,
+ const d3d11::Format &format,
+ const D3D11_SUBRESOURCE_DATA *initData,
+ TextureHelper11 *textureOut);
+
+ gl::Error allocateTexture(const D3D11_TEXTURE3D_DESC &desc,
+ const d3d11::Format &format,
+ const D3D11_SUBRESOURCE_DATA *initData,
+ TextureHelper11 *textureOut);
+
+ gl::Error clearRenderTarget(RenderTargetD3D *renderTarget,
+ const gl::ColorF &clearColorValue,
+ const float clearDepthValue,
+ const unsigned int clearStencilValue) override;
+
+ bool canSelectViewInVertexShader() const override;
private:
- gl::Error drawArraysImpl(const gl::Data &data,
- GLenum mode,
- GLsizei count,
- GLsizei instances) override;
- gl::Error drawElementsImpl(const gl::Data &data,
- const TranslatedIndexData &indexInfo,
- GLenum mode,
- GLsizei count,
- GLenum type,
- const GLvoid *indices,
- GLsizei instances) override;
-
- void generateCaps(gl::Caps *outCaps, gl::TextureCapsMap *outTextureCaps,
+ void generateCaps(gl::Caps *outCaps,
+ gl::TextureCapsMap *outTextureCaps,
gl::Extensions *outExtensions,
gl::Limitations *outLimitations) const override;
- WorkaroundsD3D generateWorkarounds() const override;
+ angle::WorkaroundsD3D generateWorkarounds() const override;
- gl::Error drawLineLoop(const gl::Data &data,
+ gl::Error drawLineLoop(const gl::Context *context,
GLsizei count,
GLenum type,
- const GLvoid *indices,
- const TranslatedIndexData *indexInfo,
+ const void *indices,
+ int baseVertex,
int instances);
- gl::Error drawTriangleFan(const gl::Data &data,
+ gl::Error drawTriangleFan(const gl::Context *context,
GLsizei count,
GLenum type,
- const GLvoid *indices,
- int minIndex,
+ const void *indices,
+ int baseVertex,
int instances);
- ID3D11Texture2D *resolveMultisampledTexture(ID3D11Texture2D *source, unsigned int subresource);
+ gl::ErrorOrResult<TextureHelper11> resolveMultisampledTexture(const gl::Context *context,
+ RenderTarget11 *renderTarget,
+ bool depth,
+ bool stencil);
void populateRenderer11DeviceCaps();
void updateHistograms();
- HMODULE mD3d11Module;
- HMODULE mDxgiModule;
- HMODULE mDCompModule;
- std::vector<D3D_FEATURE_LEVEL> mAvailableFeatureLevels;
- D3D_DRIVER_TYPE mRequestedDriverType;
- bool mCreatedWithDeviceEXT;
- DeviceD3D *mEGLDevice;
+ gl::Error copyImageInternal(const gl::Context *context,
+ const gl::Framebuffer *framebuffer,
+ const gl::Rectangle &sourceRect,
+ GLenum destFormat,
+ const gl::Offset &destOffset,
+ RenderTargetD3D *destRenderTarget);
- HLSLCompiler mCompiler;
+ gl::SupportedSampleSet generateSampleSetForEGLConfig(
+ const gl::TextureCaps &colorBufferFormatCaps,
+ const gl::TextureCaps &depthStencilBufferFormatCaps) const;
+ HRESULT callD3D11CreateDevice(PFN_D3D11_CREATE_DEVICE createDevice, bool debug);
egl::Error initializeD3DDevice();
- void initializeDevice();
+ egl::Error initializeDevice();
void releaseDeviceResources();
void release();
d3d11::ANGLED3D11DeviceType getDeviceType() const;
- RenderStateCache mStateCache;
+ gl::Error markTransformFeedbackUsage(const gl::Context *context);
- // current render target states
- uintptr_t mAppliedRTVs[gl::IMPLEMENTATION_MAX_DRAW_BUFFERS];
- uintptr_t mAppliedDSV;
+ HMODULE mD3d11Module;
+ HMODULE mDxgiModule;
+ HMODULE mDCompModule;
+ std::vector<D3D_FEATURE_LEVEL> mAvailableFeatureLevels;
+ D3D_DRIVER_TYPE mRequestedDriverType;
+ bool mCreateDebugDevice;
+ bool mCreatedWithDeviceEXT;
+ DeviceD3D *mEGLDevice;
- // Currently applied sampler states
- std::vector<bool> mForceSetVertexSamplerStates;
- std::vector<gl::SamplerState> mCurVertexSamplerStates;
+ HLSLCompiler mCompiler;
- std::vector<bool> mForceSetPixelSamplerStates;
- std::vector<gl::SamplerState> mCurPixelSamplerStates;
+ RenderStateCache mStateCache;
StateManager11 mStateManager;
- // Currently applied primitive topology
- D3D11_PRIMITIVE_TOPOLOGY mCurrentPrimitiveTopology;
-
- // Currently applied index buffer
- ID3D11Buffer *mAppliedIB;
- DXGI_FORMAT mAppliedIBFormat;
- unsigned int mAppliedIBOffset;
- bool mAppliedIBChanged;
-
- // Currently applied transform feedback buffers
- size_t mAppliedNumXFBBindings;
- ID3D11Buffer *mAppliedTFBuffers[gl::IMPLEMENTATION_MAX_TRANSFORM_FEEDBACK_BUFFERS]; // Tracks the current D3D buffers
- // in use for streamout
- GLintptr mAppliedTFOffsets[gl::IMPLEMENTATION_MAX_TRANSFORM_FEEDBACK_BUFFERS]; // Tracks the current GL-specified
- // buffer offsets to transform feedback
- // buffers
- UINT mCurrentD3DOffsets[gl::IMPLEMENTATION_MAX_TRANSFORM_FEEDBACK_BUFFERS]; // Tracks the D3D buffer offsets,
- // which may differ from GLs, due
- // to different append behavior
-
- // Currently applied shaders
- uintptr_t mAppliedVertexShader;
- uintptr_t mAppliedGeometryShader;
- uintptr_t mAppliedPixelShader;
-
- dx_VertexConstants11 mAppliedVertexConstants;
- ID3D11Buffer *mDriverConstantBufferVS;
- ID3D11Buffer *mCurrentVertexConstantBuffer;
- unsigned int mCurrentConstantBufferVS[gl::IMPLEMENTATION_MAX_VERTEX_SHADER_UNIFORM_BUFFERS];
- GLintptr mCurrentConstantBufferVSOffset[gl::IMPLEMENTATION_MAX_VERTEX_SHADER_UNIFORM_BUFFERS];
- GLsizeiptr mCurrentConstantBufferVSSize[gl::IMPLEMENTATION_MAX_VERTEX_SHADER_UNIFORM_BUFFERS];
-
- dx_PixelConstants11 mAppliedPixelConstants;
- ID3D11Buffer *mDriverConstantBufferPS;
- ID3D11Buffer *mCurrentPixelConstantBuffer;
- unsigned int mCurrentConstantBufferPS[gl::IMPLEMENTATION_MAX_FRAGMENT_SHADER_UNIFORM_BUFFERS];
- GLintptr mCurrentConstantBufferPSOffset[gl::IMPLEMENTATION_MAX_FRAGMENT_SHADER_UNIFORM_BUFFERS];
- GLsizeiptr mCurrentConstantBufferPSSize[gl::IMPLEMENTATION_MAX_FRAGMENT_SHADER_UNIFORM_BUFFERS];
-
- ID3D11Buffer *mCurrentGeometryConstantBuffer;
-
- // Vertex, index and input layouts
- VertexDataManager *mVertexDataManager;
- IndexDataManager *mIndexDataManager;
- InputLayoutCache mInputLayoutCache;
-
StreamingIndexBufferInterface *mLineLoopIB;
StreamingIndexBufferInterface *mTriangleFanIB;
@@ -429,10 +542,10 @@ class Renderer11 : public RendererD3D
Trim11 *mTrim;
// Sync query
- ID3D11Query *mSyncQuery;
+ d3d11::Query mSyncQuery;
// Created objects state tracking
- std::set<const Buffer11*> mAliveBuffers;
+ std::set<const Buffer11 *> mAliveBuffers;
double mLastHistogramUpdateTime;
@@ -440,18 +553,24 @@ class Renderer11 : public RendererD3D
Renderer11DeviceCaps mRenderer11DeviceCaps;
ID3D11DeviceContext *mDeviceContext;
ID3D11DeviceContext1 *mDeviceContext1;
+ ID3D11DeviceContext3 *mDeviceContext3;
IDXGIAdapter *mDxgiAdapter;
DXGI_ADAPTER_DESC mAdapterDescription;
char mDescription[128];
- DXGIFactory *mDxgiFactory;
-#if !defined(ANGLE_MINGW32_COMPAT)
+ IDXGIFactory *mDxgiFactory;
ID3D11Debug *mDebug;
-#endif
std::vector<GLuint> mScratchIndexDataBuffer;
+ angle::ScratchBuffer mScratchMemoryBuffer;
+
+ gl::DebugAnnotator *mAnnotator;
+
mutable Optional<bool> mSupportsShareHandles;
+ ResourceManager11 mResourceManager11;
+
+ TextureHelper11 mCachedResolveTexture;
};
-}
-#endif // LIBANGLE_RENDERER_D3D_D3D11_RENDERER11_H_
+} // namespace rx
+#endif // LIBANGLE_RENDERER_D3D_D3D11_RENDERER11_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/ResourceManager11.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/ResourceManager11.cpp
new file mode 100644
index 0000000000..c228380a34
--- /dev/null
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/ResourceManager11.cpp
@@ -0,0 +1,533 @@
+//
+// Copyright 2017 The ANGLE Project Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+//
+// ResourceManager11:
+// Centralized point of allocation for all D3D11 Resources.
+
+#include "libANGLE/renderer/d3d/d3d11/ResourceManager11.h"
+
+#include "common/debug.h"
+#include "libANGLE/renderer/d3d/d3d11/Renderer11.h"
+#include "libANGLE/renderer/d3d/d3d11/formatutils11.h"
+
+namespace rx
+{
+
+namespace
+{
+
+constexpr uint8_t kDebugInitTextureDataValue = 0x48;
+constexpr FLOAT kDebugColorInitClearValue[4] = {0.3f, 0.5f, 0.7f, 0.5f};
+constexpr FLOAT kDebugDepthInitValue = 0.2f;
+constexpr UINT8 kDebugStencilInitValue = 3;
+
+uint64_t ComputeMippedMemoryUsage(unsigned int width,
+ unsigned int height,
+ unsigned int depth,
+ uint64_t pixelSize,
+ unsigned int mipLevels)
+{
+ uint64_t sizeSum = 0;
+
+ for (unsigned int level = 0; level < mipLevels; ++level)
+ {
+ unsigned int mipWidth = std::max(width >> level, 1u);
+ unsigned int mipHeight = std::max(height >> level, 1u);
+ unsigned int mipDepth = std::max(depth >> level, 1u);
+ sizeSum += static_cast<uint64_t>(mipWidth * mipHeight * mipDepth) * pixelSize;
+ }
+
+ return sizeSum;
+}
+
+uint64_t ComputeMemoryUsage(const D3D11_TEXTURE2D_DESC *desc)
+{
+ ASSERT(desc);
+ uint64_t pixelBytes =
+ static_cast<uint64_t>(d3d11::GetDXGIFormatSizeInfo(desc->Format).pixelBytes);
+ return ComputeMippedMemoryUsage(desc->Width, desc->Height, 1, pixelBytes, desc->MipLevels);
+}
+
+uint64_t ComputeMemoryUsage(const D3D11_TEXTURE3D_DESC *desc)
+{
+ ASSERT(desc);
+ uint64_t pixelBytes =
+ static_cast<uint64_t>(d3d11::GetDXGIFormatSizeInfo(desc->Format).pixelBytes);
+ return ComputeMippedMemoryUsage(desc->Width, desc->Height, desc->Depth, pixelBytes,
+ desc->MipLevels);
+}
+
+uint64_t ComputeMemoryUsage(const D3D11_BUFFER_DESC *desc)
+{
+ ASSERT(desc);
+ return static_cast<uint64_t>(desc->ByteWidth);
+}
+
+template <typename T>
+uint64_t ComputeMemoryUsage(const T *desc)
+{
+ return 0;
+}
+
+template <ResourceType ResourceT>
+uint64_t ComputeGenericMemoryUsage(ID3D11DeviceChild *genericResource)
+{
+ auto *typedResource = static_cast<GetD3D11Type<ResourceT> *>(genericResource);
+ GetDescType<ResourceT> desc;
+ typedResource->GetDesc(&desc);
+ return ComputeMemoryUsage(&desc);
+}
+
+uint64_t ComputeGenericMemoryUsage(ResourceType resourceType, ID3D11DeviceChild *resource)
+{
+ switch (resourceType)
+ {
+ case ResourceType::Texture2D:
+ return ComputeGenericMemoryUsage<ResourceType::Texture2D>(resource);
+ case ResourceType::Texture3D:
+ return ComputeGenericMemoryUsage<ResourceType::Texture3D>(resource);
+ case ResourceType::Buffer:
+ return ComputeGenericMemoryUsage<ResourceType::Buffer>(resource);
+
+ default:
+ return 0;
+ }
+}
+
+HRESULT CreateResource(ID3D11Device *device,
+ const D3D11_BLEND_DESC *desc,
+ void * /*initData*/,
+ ID3D11BlendState **blendState)
+{
+ return device->CreateBlendState(desc, blendState);
+}
+
+HRESULT CreateResource(ID3D11Device *device,
+ const D3D11_BUFFER_DESC *desc,
+ const D3D11_SUBRESOURCE_DATA *initData,
+ ID3D11Buffer **buffer)
+{
+ return device->CreateBuffer(desc, initData, buffer);
+}
+
+HRESULT CreateResource(ID3D11Device *device,
+ const ShaderData *desc,
+ void * /*initData*/,
+ ID3D11ComputeShader **resourceOut)
+{
+ return device->CreateComputeShader(desc->get(), desc->size(), nullptr, resourceOut);
+}
+
+HRESULT CreateResource(ID3D11Device *device,
+ const D3D11_DEPTH_STENCIL_DESC *desc,
+ void * /*initData*/,
+ ID3D11DepthStencilState **resourceOut)
+{
+ return device->CreateDepthStencilState(desc, resourceOut);
+}
+
+HRESULT CreateResource(ID3D11Device *device,
+ const D3D11_DEPTH_STENCIL_VIEW_DESC *desc,
+ ID3D11Resource *resource,
+ ID3D11DepthStencilView **resourceOut)
+{
+ return device->CreateDepthStencilView(resource, desc, resourceOut);
+}
+
+HRESULT CreateResource(ID3D11Device *device,
+ const ShaderData *desc,
+ const std::vector<D3D11_SO_DECLARATION_ENTRY> *initData,
+ ID3D11GeometryShader **resourceOut)
+{
+ if (initData)
+ {
+ return device->CreateGeometryShaderWithStreamOutput(
+ desc->get(), desc->size(), initData->data(), static_cast<UINT>(initData->size()),
+ nullptr, 0, 0, nullptr, resourceOut);
+ }
+ else
+ {
+ return device->CreateGeometryShader(desc->get(), desc->size(), nullptr, resourceOut);
+ }
+}
+
+HRESULT CreateResource(ID3D11Device *device,
+ const InputElementArray *desc,
+ const ShaderData *initData,
+ ID3D11InputLayout **resourceOut)
+{
+ return device->CreateInputLayout(desc->get(), static_cast<UINT>(desc->size()), initData->get(),
+ initData->size(), resourceOut);
+}
+
+HRESULT CreateResource(ID3D11Device *device,
+ const ShaderData *desc,
+ void * /*initData*/,
+ ID3D11PixelShader **resourceOut)
+{
+ return device->CreatePixelShader(desc->get(), desc->size(), nullptr, resourceOut);
+}
+
+HRESULT CreateResource(ID3D11Device *device,
+ const D3D11_QUERY_DESC *desc,
+ void * /*initData*/,
+ ID3D11Query **resourceOut)
+{
+ return device->CreateQuery(desc, resourceOut);
+}
+
+HRESULT CreateResource(ID3D11Device *device,
+ const D3D11_RASTERIZER_DESC *desc,
+ void * /*initData*/,
+ ID3D11RasterizerState **rasterizerState)
+{
+ return device->CreateRasterizerState(desc, rasterizerState);
+}
+
+HRESULT CreateResource(ID3D11Device *device,
+ const D3D11_RENDER_TARGET_VIEW_DESC *desc,
+ ID3D11Resource *resource,
+ ID3D11RenderTargetView **renderTargetView)
+{
+ return device->CreateRenderTargetView(resource, desc, renderTargetView);
+}
+
+HRESULT CreateResource(ID3D11Device *device,
+ const D3D11_SAMPLER_DESC *desc,
+ void * /*initData*/,
+ ID3D11SamplerState **resourceOut)
+{
+ return device->CreateSamplerState(desc, resourceOut);
+}
+
+HRESULT CreateResource(ID3D11Device *device,
+ const D3D11_SHADER_RESOURCE_VIEW_DESC *desc,
+ ID3D11Resource *resource,
+ ID3D11ShaderResourceView **resourceOut)
+{
+ return device->CreateShaderResourceView(resource, desc, resourceOut);
+}
+
+HRESULT CreateResource(ID3D11Device *device,
+ const D3D11_TEXTURE2D_DESC *desc,
+ const D3D11_SUBRESOURCE_DATA *initData,
+ ID3D11Texture2D **texture)
+{
+ return device->CreateTexture2D(desc, initData, texture);
+}
+
+HRESULT CreateResource(ID3D11Device *device,
+ const D3D11_TEXTURE3D_DESC *desc,
+ const D3D11_SUBRESOURCE_DATA *initData,
+ ID3D11Texture3D **texture)
+{
+ return device->CreateTexture3D(desc, initData, texture);
+}
+
+HRESULT CreateResource(ID3D11Device *device,
+ const ShaderData *desc,
+ void * /*initData*/,
+ ID3D11VertexShader **resourceOut)
+{
+ return device->CreateVertexShader(desc->get(), desc->size(), nullptr, resourceOut);
+}
+
+DXGI_FORMAT GetTypedDepthStencilFormat(DXGI_FORMAT dxgiFormat)
+{
+ switch (dxgiFormat)
+ {
+ case DXGI_FORMAT_R16_TYPELESS:
+ return DXGI_FORMAT_D16_UNORM;
+ case DXGI_FORMAT_R24G8_TYPELESS:
+ return DXGI_FORMAT_D24_UNORM_S8_UINT;
+ case DXGI_FORMAT_R32_TYPELESS:
+ return DXGI_FORMAT_D32_FLOAT;
+ case DXGI_FORMAT_R32G8X24_TYPELESS:
+ return DXGI_FORMAT_D32_FLOAT_S8X24_UINT;
+ default:
+ return dxgiFormat;
+ }
+}
+
+template <typename DescT, typename ResourceT>
+gl::Error ClearResource(Renderer11 *renderer, const DescT *desc, ResourceT *texture)
+{
+ // No-op.
+ return gl::NoError();
+}
+
+template <>
+gl::Error ClearResource(Renderer11 *renderer,
+ const D3D11_TEXTURE2D_DESC *desc,
+ ID3D11Texture2D *texture)
+{
+ ID3D11DeviceContext *context = renderer->getDeviceContext();
+
+ if ((desc->BindFlags & D3D11_BIND_DEPTH_STENCIL) != 0)
+ {
+ D3D11_DEPTH_STENCIL_VIEW_DESC dsvDesc;
+ dsvDesc.Flags = 0;
+ dsvDesc.Format = GetTypedDepthStencilFormat(desc->Format);
+
+ const auto &format = d3d11_angle::GetFormat(dsvDesc.Format);
+ UINT clearFlags = (format.depthBits > 0 ? D3D11_CLEAR_DEPTH : 0) |
+ (format.stencilBits > 0 ? D3D11_CLEAR_STENCIL : 0);
+
+ // Must process each mip level individually.
+ for (UINT mipLevel = 0; mipLevel < desc->MipLevels; ++mipLevel)
+ {
+ if (desc->SampleDesc.Count == 0)
+ {
+ dsvDesc.Texture2D.MipSlice = mipLevel;
+ dsvDesc.ViewDimension = D3D11_DSV_DIMENSION_TEXTURE2D;
+ }
+ else
+ {
+ dsvDesc.ViewDimension = D3D11_DSV_DIMENSION_TEXTURE2DMS;
+ }
+
+ d3d11::DepthStencilView dsv;
+ ANGLE_TRY(renderer->allocateResource(dsvDesc, texture, &dsv));
+
+ context->ClearDepthStencilView(dsv.get(), clearFlags, kDebugDepthInitValue,
+ kDebugStencilInitValue);
+ }
+ }
+ else
+ {
+ ASSERT((desc->BindFlags & D3D11_BIND_RENDER_TARGET) != 0);
+ d3d11::RenderTargetView rtv;
+ ANGLE_TRY(renderer->allocateResourceNoDesc(texture, &rtv));
+
+ context->ClearRenderTargetView(rtv.get(), kDebugColorInitClearValue);
+ }
+
+ return gl::NoError();
+}
+
+template <>
+gl::Error ClearResource(Renderer11 *renderer,
+ const D3D11_TEXTURE3D_DESC *desc,
+ ID3D11Texture3D *texture)
+{
+ ID3D11DeviceContext *context = renderer->getDeviceContext();
+
+ ASSERT((desc->BindFlags & D3D11_BIND_DEPTH_STENCIL) == 0);
+ ASSERT((desc->BindFlags & D3D11_BIND_RENDER_TARGET) != 0);
+
+ d3d11::RenderTargetView rtv;
+ ANGLE_TRY(renderer->allocateResourceNoDesc(texture, &rtv));
+
+ context->ClearRenderTargetView(rtv.get(), kDebugColorInitClearValue);
+ return gl::NoError();
+}
+
+#define ANGLE_RESOURCE_STRINGIFY_OP(NAME, RESTYPE, D3D11TYPE, DESCTYPE, INITDATATYPE) #RESTYPE,
+
+constexpr std::array<const char *, NumResourceTypes> kResourceTypeNames = {
+ {ANGLE_RESOURCE_TYPE_OP(Stringify, ANGLE_RESOURCE_STRINGIFY_OP)}};
+static_assert(kResourceTypeNames[NumResourceTypes - 1] != nullptr,
+ "All members must be initialized.");
+
+} // anonymous namespace
+
+// ResourceManager11 Implementation.
+ResourceManager11::ResourceManager11()
+ : mInitializeAllocations(false),
+ mAllocatedResourceCounts({{}}),
+ mAllocatedResourceDeviceMemory({{}})
+{
+}
+
+ResourceManager11::~ResourceManager11()
+{
+ for (size_t count : mAllocatedResourceCounts)
+ {
+ ASSERT(count == 0);
+ }
+
+ for (uint64_t memorySize : mAllocatedResourceDeviceMemory)
+ {
+ ASSERT(memorySize == 0);
+ }
+}
+
+template <typename T>
+gl::Error ResourceManager11::allocate(Renderer11 *renderer,
+ const GetDescFromD3D11<T> *desc,
+ GetInitDataFromD3D11<T> *initData,
+ Resource11<T> *resourceOut)
+{
+ ID3D11Device *device = renderer->getDevice();
+ T *resource = nullptr;
+
+ GetInitDataFromD3D11<T> *shadowInitData = initData;
+ if (!shadowInitData && mInitializeAllocations)
+ {
+ shadowInitData = createInitDataIfNeeded<T>(desc);
+ }
+
+ HRESULT hr = CreateResource(device, desc, shadowInitData, &resource);
+ if (FAILED(hr))
+ {
+ ASSERT(!resource);
+ if (d3d11::isDeviceLostError(hr))
+ {
+ renderer->notifyDeviceLost();
+ }
+ return gl::OutOfMemory() << "Error allocating "
+ << std::string(kResourceTypeNames[ResourceTypeIndex<T>()]) << ". "
+ << gl::FmtHR(hr);
+ }
+
+ if (!shadowInitData && mInitializeAllocations)
+ {
+ ANGLE_TRY(ClearResource(renderer, desc, resource));
+ }
+
+ ASSERT(resource);
+ incrResource(GetResourceTypeFromD3D11<T>(), ComputeMemoryUsage(desc));
+ *resourceOut = std::move(Resource11<T>(resource, this));
+ return gl::NoError();
+}
+
+void ResourceManager11::incrResource(ResourceType resourceType, uint64_t memorySize)
+{
+ size_t typeIndex = ResourceTypeIndex(resourceType);
+
+ mAllocatedResourceCounts[typeIndex]++;
+ mAllocatedResourceDeviceMemory[typeIndex] += memorySize;
+
+ // This checks for integer overflow.
+ ASSERT(mAllocatedResourceCounts[typeIndex] > 0);
+ ASSERT(mAllocatedResourceDeviceMemory[typeIndex] >= memorySize);
+}
+
+void ResourceManager11::decrResource(ResourceType resourceType, uint64_t memorySize)
+{
+ size_t typeIndex = ResourceTypeIndex(resourceType);
+
+ ASSERT(mAllocatedResourceCounts[typeIndex] > 0);
+ mAllocatedResourceCounts[typeIndex]--;
+ ASSERT(mAllocatedResourceDeviceMemory[typeIndex] >= memorySize);
+ mAllocatedResourceDeviceMemory[typeIndex] -= memorySize;
+}
+
+void ResourceManager11::onReleaseGeneric(ResourceType resourceType, ID3D11DeviceChild *resource)
+{
+ ASSERT(resource);
+ decrResource(resourceType, ComputeGenericMemoryUsage(resourceType, resource));
+}
+
+template <>
+const D3D11_SUBRESOURCE_DATA *ResourceManager11::createInitDataIfNeeded<ID3D11Texture2D>(
+ const D3D11_TEXTURE2D_DESC *desc)
+{
+ ASSERT(desc);
+
+ if ((desc->BindFlags & (D3D11_BIND_DEPTH_STENCIL | D3D11_BIND_RENDER_TARGET)) != 0)
+ {
+ // This will be done using ClearView methods.
+ return nullptr;
+ }
+
+ size_t requiredSize = static_cast<size_t>(ComputeMemoryUsage(desc));
+ if (mZeroMemory.size() < requiredSize)
+ {
+ mZeroMemory.resize(requiredSize);
+ mZeroMemory.fill(kDebugInitTextureDataValue);
+ }
+
+ const auto &formatSizeInfo = d3d11::GetDXGIFormatSizeInfo(desc->Format);
+
+ UINT subresourceCount = desc->MipLevels * desc->ArraySize;
+ if (mShadowInitData.size() < subresourceCount)
+ {
+ mShadowInitData.resize(subresourceCount);
+ }
+
+ for (UINT mipLevel = 0; mipLevel < desc->MipLevels; ++mipLevel)
+ {
+ for (UINT arrayIndex = 0; arrayIndex < desc->ArraySize; ++arrayIndex)
+ {
+ UINT subresourceIndex = D3D11CalcSubresource(mipLevel, arrayIndex, desc->MipLevels);
+ D3D11_SUBRESOURCE_DATA *data = &mShadowInitData[subresourceIndex];
+
+ UINT levelWidth = std::max(desc->Width >> mipLevel, 1u);
+ UINT levelHeight = std::max(desc->Height >> mipLevel, 1u);
+
+ data->SysMemPitch = levelWidth * formatSizeInfo.pixelBytes;
+ data->SysMemSlicePitch = data->SysMemPitch * levelHeight;
+ data->pSysMem = mZeroMemory.data();
+ }
+ }
+
+ return mShadowInitData.data();
+}
+
+template <>
+const D3D11_SUBRESOURCE_DATA *ResourceManager11::createInitDataIfNeeded<ID3D11Texture3D>(
+ const D3D11_TEXTURE3D_DESC *desc)
+{
+ ASSERT(desc);
+
+ if ((desc->BindFlags & D3D11_BIND_RENDER_TARGET) != 0)
+ {
+ // This will be done using ClearView methods.
+ return nullptr;
+ }
+
+ size_t requiredSize = static_cast<size_t>(ComputeMemoryUsage(desc));
+ if (mZeroMemory.size() < requiredSize)
+ {
+ mZeroMemory.resize(requiredSize);
+ mZeroMemory.fill(kDebugInitTextureDataValue);
+ }
+
+ const auto &formatSizeInfo = d3d11::GetDXGIFormatSizeInfo(desc->Format);
+
+ UINT subresourceCount = desc->MipLevels;
+ if (mShadowInitData.size() < subresourceCount)
+ {
+ mShadowInitData.resize(subresourceCount);
+ }
+
+ for (UINT mipLevel = 0; mipLevel < desc->MipLevels; ++mipLevel)
+ {
+ UINT subresourceIndex = D3D11CalcSubresource(mipLevel, 0, desc->MipLevels);
+ D3D11_SUBRESOURCE_DATA *data = &mShadowInitData[subresourceIndex];
+
+ UINT levelWidth = std::max(desc->Width >> mipLevel, 1u);
+ UINT levelHeight = std::max(desc->Height >> mipLevel, 1u);
+
+ data->SysMemPitch = levelWidth * formatSizeInfo.pixelBytes;
+ data->SysMemSlicePitch = data->SysMemPitch * levelHeight;
+ data->pSysMem = mZeroMemory.data();
+ }
+
+ return mShadowInitData.data();
+}
+
+template <typename T>
+GetInitDataFromD3D11<T> *ResourceManager11::createInitDataIfNeeded(const GetDescFromD3D11<T> *desc)
+{
+ // No-op.
+ return nullptr;
+}
+
+void ResourceManager11::setAllocationsInitialized(bool initialize)
+{
+ mInitializeAllocations = initialize;
+}
+
+#define ANGLE_INSTANTIATE_OP(NAME, RESTYPE, D3D11TYPE, DESCTYPE, INITDATATYPE) \
+ \
+template \
+gl::Error \
+ ResourceManager11::allocate(Renderer11 *, const DESCTYPE *, INITDATATYPE *, \
+ Resource11<D3D11TYPE> *);
+
+ANGLE_RESOURCE_TYPE_OP(Instantitate, ANGLE_INSTANTIATE_OP)
+} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/ResourceManager11.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/ResourceManager11.h
new file mode 100644
index 0000000000..0bdde9f8b6
--- /dev/null
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/ResourceManager11.h
@@ -0,0 +1,366 @@
+//
+// Copyright 2017 The ANGLE Project Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+//
+// ResourceManager11:
+// Centralized point of allocation for all D3D11 Resources.
+
+#ifndef LIBANGLE_RENDERER_D3D_D3D11_RESOURCEFACTORY11_H_
+#define LIBANGLE_RENDERER_D3D_D3D11_RESOURCEFACTORY11_H_
+
+#include <array>
+#include <memory>
+
+#include "common/MemoryBuffer.h"
+#include "common/angleutils.h"
+#include "common/debug.h"
+#include "libANGLE/Error.h"
+#include "libANGLE/renderer/renderer_utils.h"
+
+namespace rx
+{
+// These two methods are declared here to prevent circular includes.
+namespace d3d11
+{
+HRESULT SetDebugName(ID3D11DeviceChild *resource, const char *name);
+
+template <typename T>
+HRESULT SetDebugName(angle::ComPtr<T> &resource, const char *name)
+{
+ return SetDebugName(resource.Get(), name);
+}
+} // namespace d3d11
+
+class Renderer11;
+class ResourceManager11;
+template <typename T>
+class SharedResource11;
+class TextureHelper11;
+
+using InputElementArray = WrappedArray<D3D11_INPUT_ELEMENT_DESC>;
+using ShaderData = WrappedArray<uint8_t>;
+
+// Format: ResourceType, D3D11 type, DESC type, init data type.
+#define ANGLE_RESOURCE_TYPE_OP(NAME, OP) \
+ OP(NAME, BlendState, ID3D11BlendState, D3D11_BLEND_DESC, void) \
+ OP(NAME, Buffer, ID3D11Buffer, D3D11_BUFFER_DESC, const D3D11_SUBRESOURCE_DATA) \
+ OP(NAME, ComputeShader, ID3D11ComputeShader, ShaderData, void) \
+ OP(NAME, DepthStencilState, ID3D11DepthStencilState, D3D11_DEPTH_STENCIL_DESC, void) \
+ OP(NAME, DepthStencilView, ID3D11DepthStencilView, D3D11_DEPTH_STENCIL_VIEW_DESC, \
+ ID3D11Resource) \
+ OP(NAME, GeometryShader, ID3D11GeometryShader, ShaderData, \
+ const std::vector<D3D11_SO_DECLARATION_ENTRY>) \
+ OP(NAME, InputLayout, ID3D11InputLayout, InputElementArray, const ShaderData) \
+ OP(NAME, PixelShader, ID3D11PixelShader, ShaderData, void) \
+ OP(NAME, Query, ID3D11Query, D3D11_QUERY_DESC, void) \
+ OP(NAME, RasterizerState, ID3D11RasterizerState, D3D11_RASTERIZER_DESC, void) \
+ OP(NAME, RenderTargetView, ID3D11RenderTargetView, D3D11_RENDER_TARGET_VIEW_DESC, \
+ ID3D11Resource) \
+ OP(NAME, SamplerState, ID3D11SamplerState, D3D11_SAMPLER_DESC, void) \
+ OP(NAME, ShaderResourceView, ID3D11ShaderResourceView, D3D11_SHADER_RESOURCE_VIEW_DESC, \
+ ID3D11Resource) \
+ OP(NAME, Texture2D, ID3D11Texture2D, D3D11_TEXTURE2D_DESC, const D3D11_SUBRESOURCE_DATA) \
+ OP(NAME, Texture3D, ID3D11Texture3D, D3D11_TEXTURE3D_DESC, const D3D11_SUBRESOURCE_DATA) \
+ OP(NAME, VertexShader, ID3D11VertexShader, ShaderData, void)
+
+#define ANGLE_RESOURCE_TYPE_LIST(NAME, RESTYPE, D3D11TYPE, DESCTYPE, INITDATATYPE) RESTYPE,
+
+enum class ResourceType
+{
+ ANGLE_RESOURCE_TYPE_OP(List, ANGLE_RESOURCE_TYPE_LIST) Last
+};
+
+#undef ANGLE_RESOURCE_TYPE_LIST
+
+constexpr size_t ResourceTypeIndex(ResourceType resourceType)
+{
+ return static_cast<size_t>(resourceType);
+}
+
+constexpr size_t NumResourceTypes = ResourceTypeIndex(ResourceType::Last);
+
+#define ANGLE_RESOURCE_TYPE_TO_D3D11(NAME, RESTYPE, D3D11TYPE, DESCTYPE, INITDATATYPE) \
+ \
+template<> struct NAME<ResourceType::RESTYPE> \
+ { \
+ using Value = D3D11TYPE; \
+ };
+
+#define ANGLE_RESOURCE_TYPE_TO_DESC(NAME, RESTYPE, D3D11TYPE, DESCTYPE, INITDATATYPE) \
+ \
+template<> struct NAME<ResourceType::RESTYPE> \
+ { \
+ using Value = DESCTYPE; \
+ };
+
+#define ANGLE_RESOURCE_TYPE_TO_INIT_DATA(NAME, RESTYPE, D3D11TYPE, DESCTYPE, INITDATATYPE) \
+ \
+template<> struct NAME<ResourceType::RESTYPE> \
+ { \
+ using Value = INITDATATYPE; \
+ };
+
+#define ANGLE_RESOURCE_TYPE_TO_TYPE(NAME, OP) \
+ template <ResourceType Param> \
+ struct NAME; \
+ ANGLE_RESOURCE_TYPE_OP(NAME, OP) \
+ \
+template<ResourceType Param> struct NAME \
+ { \
+ }; \
+ \
+template<ResourceType Param> using Get##NAME = typename NAME<Param>::Value;
+
+ANGLE_RESOURCE_TYPE_TO_TYPE(D3D11Type, ANGLE_RESOURCE_TYPE_TO_D3D11)
+ANGLE_RESOURCE_TYPE_TO_TYPE(DescType, ANGLE_RESOURCE_TYPE_TO_DESC)
+ANGLE_RESOURCE_TYPE_TO_TYPE(InitDataType, ANGLE_RESOURCE_TYPE_TO_INIT_DATA)
+
+#undef ANGLE_RESOURCE_TYPE_TO_D3D11
+#undef ANGLE_RESOURCE_TYPE_TO_DESC
+#undef ANGLE_RESOURCE_TYPE_TO_INIT_DATA
+#undef ANGLE_RESOURCE_TYPE_TO_TYPE
+
+#define ANGLE_TYPE_TO_RESOURCE_TYPE(NAME, OP) \
+ template <typename Param> \
+ struct NAME; \
+ ANGLE_RESOURCE_TYPE_OP(NAME, OP) \
+ \
+template<typename Param> struct NAME \
+ { \
+ }; \
+ \
+template<typename Param> constexpr ResourceType Get##NAME() \
+ { \
+ return NAME<Param>::Value; \
+ }
+
+#define ANGLE_D3D11_TO_RESOURCE_TYPE(NAME, RESTYPE, D3D11TYPE, DESCTYPE, INITDATATYPE) \
+ \
+template<> struct NAME<D3D11TYPE> \
+ { \
+ static constexpr ResourceType Value = ResourceType::RESTYPE; \
+ };
+
+ANGLE_TYPE_TO_RESOURCE_TYPE(ResourceTypeFromD3D11, ANGLE_D3D11_TO_RESOURCE_TYPE)
+
+#undef ANGLE_D3D11_TO_RESOURCE_TYPE
+#undef ANGLE_TYPE_TO_RESOURCE_TYPE
+
+template <typename T>
+using GetDescFromD3D11 = GetDescType<ResourceTypeFromD3D11<T>::Value>;
+
+template <typename T>
+using GetInitDataFromD3D11 = GetInitDataType<ResourceTypeFromD3D11<T>::Value>;
+
+template <typename T>
+constexpr size_t ResourceTypeIndex()
+{
+ return static_cast<size_t>(GetResourceTypeFromD3D11<T>());
+}
+
+template <typename T>
+struct TypedData
+{
+ TypedData() {}
+ ~TypedData();
+
+ T *object = nullptr;
+ ResourceManager11 *manager = nullptr;
+};
+
+// Smart pointer type. Wraps the resource and a factory for safe deletion.
+template <typename T, template <class> class Pointer, typename DataT>
+class Resource11Base : angle::NonCopyable
+{
+ public:
+ T *get() const { return mData->object; }
+ T *const *getPointer() const { return &mData->object; }
+
+ void setDebugName(const char *name) { d3d11::SetDebugName(mData->object, name); }
+
+ void set(T *object)
+ {
+ ASSERT(!valid());
+ mData->object = object;
+ }
+
+ bool valid() const { return (mData->object != nullptr); }
+
+ void reset()
+ {
+ if (valid())
+ mData.reset(new DataT());
+ }
+
+ ResourceSerial getSerial() const
+ {
+ return ResourceSerial(reinterpret_cast<uintptr_t>(mData->object));
+ }
+
+ protected:
+ friend class TextureHelper11;
+
+ Resource11Base() : mData(new DataT()) {}
+
+ Resource11Base(Resource11Base &&movedObj) : mData(new DataT())
+ {
+ std::swap(mData, movedObj.mData);
+ }
+
+ virtual ~Resource11Base() { mData.reset(); }
+
+ Resource11Base &operator=(Resource11Base &&movedObj)
+ {
+ std::swap(mData, movedObj.mData);
+ return *this;
+ }
+
+ Pointer<DataT> mData;
+};
+
+template <typename T>
+using UniquePtr = typename std::unique_ptr<T, std::default_delete<T>>;
+
+template <typename ResourceT>
+class Resource11 : public Resource11Base<ResourceT, UniquePtr, TypedData<ResourceT>>
+{
+ public:
+ Resource11() {}
+ Resource11(Resource11 &&other)
+ : Resource11Base<ResourceT, UniquePtr, TypedData<ResourceT>>(std::move(other))
+ {
+ }
+ Resource11 &operator=(Resource11 &&other)
+ {
+ std::swap(this->mData, other.mData);
+ return *this;
+ }
+
+ private:
+ template <typename T>
+ friend class SharedResource11;
+ friend class ResourceManager11;
+
+ Resource11(ResourceT *object, ResourceManager11 *manager)
+ {
+ this->mData->object = object;
+ this->mData->manager = manager;
+ }
+};
+
+template <typename T>
+class SharedResource11 : public Resource11Base<T, std::shared_ptr, TypedData<T>>
+{
+ public:
+ SharedResource11() {}
+ SharedResource11(SharedResource11 &&movedObj)
+ : Resource11Base<T, std::shared_ptr, TypedData<T>>(std::move(movedObj))
+ {
+ }
+
+ SharedResource11 &operator=(SharedResource11 &&other)
+ {
+ std::swap(this->mData, other.mData);
+ return *this;
+ }
+
+ SharedResource11 makeCopy() const
+ {
+ SharedResource11 copy;
+ copy.mData = this->mData;
+ return std::move(copy);
+ }
+
+ private:
+ friend class ResourceManager11;
+ SharedResource11(Resource11<T> &&obj) : Resource11Base<T, std::shared_ptr, TypedData<T>>()
+ {
+ std::swap(this->mData->manager, obj.mData->manager);
+
+ // Can't use std::swap because of ID3D11Resource.
+ auto temp = this->mData->object;
+ this->mData->object = obj.mData->object;
+ obj.mData->object = static_cast<T *>(temp);
+ }
+};
+
+class ResourceManager11 final : angle::NonCopyable
+{
+ public:
+ ResourceManager11();
+ ~ResourceManager11();
+
+ template <typename T>
+ gl::Error allocate(Renderer11 *renderer,
+ const GetDescFromD3D11<T> *desc,
+ GetInitDataFromD3D11<T> *initData,
+ Resource11<T> *resourceOut);
+
+ template <typename T>
+ gl::Error allocate(Renderer11 *renderer,
+ const GetDescFromD3D11<T> *desc,
+ GetInitDataFromD3D11<T> *initData,
+ SharedResource11<T> *sharedRes)
+ {
+ Resource11<T> res;
+ ANGLE_TRY(allocate(renderer, desc, initData, &res));
+ *sharedRes = std::move(res);
+ return gl::NoError();
+ }
+
+ template <typename T>
+ void onRelease(T *resource)
+ {
+ onReleaseGeneric(GetResourceTypeFromD3D11<T>(), resource);
+ }
+
+ void onReleaseGeneric(ResourceType resourceType, ID3D11DeviceChild *resource);
+
+ void setAllocationsInitialized(bool initialize);
+
+ private:
+ void incrResource(ResourceType resourceType, uint64_t memorySize);
+ void decrResource(ResourceType resourceType, uint64_t memorySize);
+
+ template <typename T>
+ GetInitDataFromD3D11<T> *createInitDataIfNeeded(const GetDescFromD3D11<T> *desc);
+
+ bool mInitializeAllocations;
+
+ std::array<size_t, NumResourceTypes> mAllocatedResourceCounts;
+ std::array<uint64_t, NumResourceTypes> mAllocatedResourceDeviceMemory;
+ angle::MemoryBuffer mZeroMemory;
+
+ std::vector<D3D11_SUBRESOURCE_DATA> mShadowInitData;
+};
+
+template <typename ResourceT>
+TypedData<ResourceT>::~TypedData()
+{
+ if (object)
+ {
+ // We can have a nullptr factory when holding passed-in resources.
+ if (manager)
+ {
+ manager->onRelease(object);
+ }
+ object->Release();
+ }
+}
+
+#define ANGLE_RESOURCE_TYPE_CLASS(NAME, RESTYPE, D3D11TYPE, DESCTYPE, INITDATATYPE) \
+ using RESTYPE = Resource11<D3D11TYPE>;
+
+namespace d3d11
+{
+ANGLE_RESOURCE_TYPE_OP(ClassList, ANGLE_RESOURCE_TYPE_CLASS)
+
+using SharedSRV = SharedResource11<ID3D11ShaderResourceView>;
+} // namespace d3d11
+
+#undef ANGLE_RESOURCE_TYPE_CLASS
+
+} // namespace rx
+
+#endif // LIBANGLE_RENDERER_D3D_D3D11_RESOURCEFACTORY11_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/ShaderExecutable11.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/ShaderExecutable11.cpp
index 4da51afe49..73a530add0 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/ShaderExecutable11.cpp
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/ShaderExecutable11.cpp
@@ -13,86 +13,107 @@
namespace rx
{
-ShaderExecutable11::ShaderExecutable11(const void *function, size_t length, ID3D11PixelShader *executable)
- : ShaderExecutableD3D(function, length)
+ShaderExecutable11::ShaderExecutable11(const void *function,
+ size_t length,
+ d3d11::PixelShader &&executable)
+ : ShaderExecutableD3D(function, length),
+ mPixelExecutable(std::move(executable)),
+ mVertexExecutable(),
+ mGeometryExecutable(),
+ mStreamOutExecutable(),
+ mComputeExecutable()
{
- mPixelExecutable = executable;
- mVertexExecutable = NULL;
- mGeometryExecutable = NULL;
- mStreamOutExecutable = NULL;
}
-ShaderExecutable11::ShaderExecutable11(const void *function, size_t length, ID3D11VertexShader *executable, ID3D11GeometryShader *streamOut)
- : ShaderExecutableD3D(function, length)
+ShaderExecutable11::ShaderExecutable11(const void *function,
+ size_t length,
+ d3d11::VertexShader &&executable,
+ d3d11::GeometryShader &&streamOut)
+ : ShaderExecutableD3D(function, length),
+ mPixelExecutable(),
+ mVertexExecutable(std::move(executable)),
+ mGeometryExecutable(),
+ mStreamOutExecutable(std::move(streamOut)),
+ mComputeExecutable()
{
- mVertexExecutable = executable;
- mPixelExecutable = NULL;
- mGeometryExecutable = NULL;
- mStreamOutExecutable = streamOut;
}
-ShaderExecutable11::ShaderExecutable11(const void *function, size_t length, ID3D11GeometryShader *executable)
- : ShaderExecutableD3D(function, length)
+ShaderExecutable11::ShaderExecutable11(const void *function,
+ size_t length,
+ d3d11::GeometryShader &&executable)
+ : ShaderExecutableD3D(function, length),
+ mPixelExecutable(),
+ mVertexExecutable(),
+ mGeometryExecutable(std::move(executable)),
+ mStreamOutExecutable(),
+ mComputeExecutable()
+{
+}
+
+ShaderExecutable11::ShaderExecutable11(const void *function,
+ size_t length,
+ d3d11::ComputeShader &&executable)
+ : ShaderExecutableD3D(function, length),
+ mPixelExecutable(),
+ mVertexExecutable(),
+ mGeometryExecutable(),
+ mStreamOutExecutable(),
+ mComputeExecutable(std::move(executable))
{
- mGeometryExecutable = executable;
- mVertexExecutable = NULL;
- mPixelExecutable = NULL;
- mStreamOutExecutable = NULL;
}
ShaderExecutable11::~ShaderExecutable11()
{
- SafeRelease(mVertexExecutable);
- SafeRelease(mPixelExecutable);
- SafeRelease(mGeometryExecutable);
- SafeRelease(mStreamOutExecutable);
}
-ID3D11VertexShader *ShaderExecutable11::getVertexShader() const
+const d3d11::VertexShader &ShaderExecutable11::getVertexShader() const
{
return mVertexExecutable;
}
-ID3D11PixelShader *ShaderExecutable11::getPixelShader() const
+const d3d11::PixelShader &ShaderExecutable11::getPixelShader() const
{
return mPixelExecutable;
}
-ID3D11GeometryShader *ShaderExecutable11::getGeometryShader() const
+const d3d11::GeometryShader &ShaderExecutable11::getGeometryShader() const
{
return mGeometryExecutable;
}
-ID3D11GeometryShader *ShaderExecutable11::getStreamOutShader() const
+const d3d11::GeometryShader &ShaderExecutable11::getStreamOutShader() const
{
return mStreamOutExecutable;
}
-UniformStorage11::UniformStorage11(Renderer11 *renderer, size_t initialSize)
- : UniformStorageD3D(initialSize),
- mConstantBuffer(NULL)
+const d3d11::ComputeShader &ShaderExecutable11::getComputeShader() const
{
- ID3D11Device *d3d11Device = renderer->getDevice();
+ return mComputeExecutable;
+}
- if (initialSize > 0)
- {
- D3D11_BUFFER_DESC constantBufferDescription = {0};
- constantBufferDescription.ByteWidth = static_cast<unsigned int>(initialSize);
- constantBufferDescription.Usage = D3D11_USAGE_DYNAMIC;
- constantBufferDescription.BindFlags = D3D11_BIND_CONSTANT_BUFFER;
- constantBufferDescription.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE;
- constantBufferDescription.MiscFlags = 0;
- constantBufferDescription.StructureByteStride = 0;
-
- HRESULT result = d3d11Device->CreateBuffer(&constantBufferDescription, NULL, &mConstantBuffer);
- UNUSED_ASSERTION_VARIABLE(result);
- ASSERT(SUCCEEDED(result));
- }
+UniformStorage11::UniformStorage11(size_t initialSize)
+ : UniformStorageD3D(initialSize), mConstantBuffer()
+{
}
UniformStorage11::~UniformStorage11()
{
- SafeRelease(mConstantBuffer);
}
+gl::Error UniformStorage11::getConstantBuffer(Renderer11 *renderer, const d3d11::Buffer **bufferOut)
+{
+ if (size() > 0 && !mConstantBuffer.valid())
+ {
+ D3D11_BUFFER_DESC desc = {0};
+ desc.ByteWidth = static_cast<unsigned int>(size());
+ desc.Usage = D3D11_USAGE_DEFAULT;
+ desc.BindFlags = D3D11_BIND_CONSTANT_BUFFER;
+
+ ANGLE_TRY(renderer->allocateResource(desc, &mConstantBuffer));
+ }
+
+ *bufferOut = &mConstantBuffer;
+ return gl::NoError();
}
+
+} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/ShaderExecutable11.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/ShaderExecutable11.h
index 379f39fe53..3f417578a3 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/ShaderExecutable11.h
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/ShaderExecutable11.h
@@ -11,6 +11,7 @@
#define LIBANGLE_RENDERER_D3D_D3D11_SHADEREXECUTABLE11_H_
#include "libANGLE/renderer/d3d/ShaderExecutableD3D.h"
+#include "libANGLE/renderer/d3d/d3d11/ResourceManager11.h"
namespace rx
{
@@ -20,36 +21,42 @@ class UniformStorage11;
class ShaderExecutable11 : public ShaderExecutableD3D
{
public:
- ShaderExecutable11(const void *function, size_t length, ID3D11PixelShader *executable);
- ShaderExecutable11(const void *function, size_t length, ID3D11VertexShader *executable, ID3D11GeometryShader *streamOut);
- ShaderExecutable11(const void *function, size_t length, ID3D11GeometryShader *executable);
-
- virtual ~ShaderExecutable11();
-
- ID3D11PixelShader *getPixelShader() const;
- ID3D11VertexShader *getVertexShader() const;
- ID3D11GeometryShader *getGeometryShader() const;
- ID3D11GeometryShader *getStreamOutShader() const;
+ ShaderExecutable11(const void *function, size_t length, d3d11::PixelShader &&executable);
+ ShaderExecutable11(const void *function,
+ size_t length,
+ d3d11::VertexShader &&executable,
+ d3d11::GeometryShader &&streamOut);
+ ShaderExecutable11(const void *function, size_t length, d3d11::GeometryShader &&executable);
+ ShaderExecutable11(const void *function, size_t length, d3d11::ComputeShader &&executable);
+
+ ~ShaderExecutable11() override;
+
+ const d3d11::PixelShader &getPixelShader() const;
+ const d3d11::VertexShader &getVertexShader() const;
+ const d3d11::GeometryShader &getGeometryShader() const;
+ const d3d11::GeometryShader &getStreamOutShader() const;
+ const d3d11::ComputeShader &getComputeShader() const;
private:
- ID3D11PixelShader *mPixelExecutable;
- ID3D11VertexShader *mVertexExecutable;
- ID3D11GeometryShader *mGeometryExecutable;
- ID3D11GeometryShader *mStreamOutExecutable;
+ d3d11::PixelShader mPixelExecutable;
+ d3d11::VertexShader mVertexExecutable;
+ d3d11::GeometryShader mGeometryExecutable;
+ d3d11::GeometryShader mStreamOutExecutable;
+ d3d11::ComputeShader mComputeExecutable;
};
class UniformStorage11 : public UniformStorageD3D
{
public:
- UniformStorage11(Renderer11 *renderer, size_t initialSize);
- virtual ~UniformStorage11();
+ UniformStorage11(size_t initialSize);
+ ~UniformStorage11() override;
- ID3D11Buffer *getConstantBuffer() const { return mConstantBuffer; }
+ gl::Error getConstantBuffer(Renderer11 *renderer, const d3d11::Buffer **bufferOut);
private:
- ID3D11Buffer *mConstantBuffer;
+ d3d11::Buffer mConstantBuffer;
};
-}
+} // namespace rx
#endif // LIBANGLE_RENDERER_D3D_D3D11_SHADEREXECUTABLE11_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/StateManager11.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/StateManager11.cpp
index aa34fd4de8..e9902d3f14 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/StateManager11.cpp
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/StateManager11.cpp
@@ -8,11 +8,22 @@
#include "libANGLE/renderer/d3d/d3d11/StateManager11.h"
-#include "common/BitSetIterator.h"
+#include "common/bitset_utils.h"
#include "common/utilities.h"
+#include "libANGLE/Context.h"
+#include "libANGLE/Query.h"
+#include "libANGLE/VertexArray.h"
+#include "libANGLE/renderer/d3d/TextureD3D.h"
+#include "libANGLE/renderer/d3d/d3d11/Buffer11.h"
+#include "libANGLE/renderer/d3d/d3d11/Context11.h"
#include "libANGLE/renderer/d3d/d3d11/Framebuffer11.h"
-#include "libANGLE/renderer/d3d/d3d11/Renderer11.h"
+#include "libANGLE/renderer/d3d/d3d11/IndexBuffer11.h"
#include "libANGLE/renderer/d3d/d3d11/RenderTarget11.h"
+#include "libANGLE/renderer/d3d/d3d11/Renderer11.h"
+#include "libANGLE/renderer/d3d/d3d11/ShaderExecutable11.h"
+#include "libANGLE/renderer/d3d/d3d11/TextureStorage11.h"
+#include "libANGLE/renderer/d3d/d3d11/TransformFeedback11.h"
+#include "libANGLE/renderer/d3d/d3d11/VertexArray11.h"
namespace rx
{
@@ -22,15 +33,16 @@ namespace
bool ImageIndexConflictsWithSRV(const gl::ImageIndex &index, D3D11_SHADER_RESOURCE_VIEW_DESC desc)
{
unsigned mipLevel = index.mipIndex;
- unsigned layerIndex = index.layerIndex;
+ GLint layerIndex = index.layerIndex;
GLenum type = index.type;
switch (desc.ViewDimension)
{
case D3D11_SRV_DIMENSION_TEXTURE2D:
{
- unsigned maxSrvMip = desc.Texture2D.MipLevels + desc.Texture2D.MostDetailedMip;
- maxSrvMip = (desc.Texture2D.MipLevels == -1) ? INT_MAX : maxSrvMip;
+ bool allLevels = (desc.Texture2D.MipLevels == std::numeric_limits<UINT>::max());
+ unsigned int maxSrvMip = desc.Texture2D.MipLevels + desc.Texture2D.MostDetailedMip;
+ maxSrvMip = allLevels ? INT_MAX : maxSrvMip;
unsigned mipMin = index.mipIndex;
unsigned mipMax = (layerIndex == -1) ? INT_MAX : layerIndex;
@@ -42,22 +54,25 @@ bool ImageIndexConflictsWithSRV(const gl::ImageIndex &index, D3D11_SHADER_RESOUR
case D3D11_SRV_DIMENSION_TEXTURE2DARRAY:
{
- unsigned maxSrvMip =
+ bool allLevels = (desc.Texture2DArray.MipLevels == std::numeric_limits<UINT>::max());
+ unsigned int maxSrvMip =
desc.Texture2DArray.MipLevels + desc.Texture2DArray.MostDetailedMip;
- maxSrvMip = (desc.Texture2DArray.MipLevels == -1) ? INT_MAX : maxSrvMip;
+ maxSrvMip = allLevels ? INT_MAX : maxSrvMip;
unsigned maxSlice = desc.Texture2DArray.FirstArraySlice + desc.Texture2DArray.ArraySize;
// Cube maps can be mapped to Texture2DArray SRVs
return (type == GL_TEXTURE_2D_ARRAY || gl::IsCubeMapTextureTarget(type)) &&
desc.Texture2DArray.MostDetailedMip <= mipLevel && mipLevel < maxSrvMip &&
- desc.Texture2DArray.FirstArraySlice <= layerIndex && layerIndex < maxSlice;
+ desc.Texture2DArray.FirstArraySlice <= static_cast<UINT>(layerIndex) &&
+ static_cast<UINT>(layerIndex) < maxSlice;
}
case D3D11_SRV_DIMENSION_TEXTURECUBE:
{
- unsigned maxSrvMip = desc.TextureCube.MipLevels + desc.TextureCube.MostDetailedMip;
- maxSrvMip = (desc.TextureCube.MipLevels == -1) ? INT_MAX : maxSrvMip;
+ bool allLevels = (desc.TextureCube.MipLevels == std::numeric_limits<UINT>::max());
+ unsigned int maxSrvMip = desc.TextureCube.MipLevels + desc.TextureCube.MostDetailedMip;
+ maxSrvMip = allLevels ? INT_MAX : maxSrvMip;
return gl::IsCubeMapTextureTarget(type) &&
desc.TextureCube.MostDetailedMip <= mipLevel && mipLevel < maxSrvMip;
@@ -65,8 +80,9 @@ bool ImageIndexConflictsWithSRV(const gl::ImageIndex &index, D3D11_SHADER_RESOUR
case D3D11_SRV_DIMENSION_TEXTURE3D:
{
- unsigned maxSrvMip = desc.Texture3D.MipLevels + desc.Texture3D.MostDetailedMip;
- maxSrvMip = (desc.Texture3D.MipLevels == -1) ? INT_MAX : maxSrvMip;
+ bool allLevels = (desc.Texture3D.MipLevels == std::numeric_limits<UINT>::max());
+ unsigned int maxSrvMip = desc.Texture3D.MipLevels + desc.Texture3D.MostDetailedMip;
+ maxSrvMip = allLevels ? INT_MAX : maxSrvMip;
return type == GL_TEXTURE_3D && desc.Texture3D.MostDetailedMip <= mipLevel &&
mipLevel < maxSrvMip;
@@ -82,15 +98,97 @@ bool ImageIndexConflictsWithSRV(const gl::ImageIndex &index, D3D11_SHADER_RESOUR
// Does *not* increment the resource ref count!!
ID3D11Resource *GetViewResource(ID3D11View *view)
{
- ID3D11Resource *resource = NULL;
+ ID3D11Resource *resource = nullptr;
ASSERT(view);
view->GetResource(&resource);
resource->Release();
return resource;
}
+int GetWrapBits(GLenum wrap)
+{
+ switch (wrap)
+ {
+ case GL_CLAMP_TO_EDGE:
+ return 0x1;
+ case GL_REPEAT:
+ return 0x2;
+ case GL_MIRRORED_REPEAT:
+ return 0x3;
+ default:
+ UNREACHABLE();
+ return 0;
+ }
+}
+
+Optional<size_t> FindFirstNonInstanced(
+ const std::vector<const TranslatedAttribute *> &currentAttributes)
+{
+ for (size_t index = 0; index < currentAttributes.size(); ++index)
+ {
+ if (currentAttributes[index]->divisor == 0)
+ {
+ return Optional<size_t>(index);
+ }
+ }
+
+ return Optional<size_t>::Invalid();
+}
+
+void SortAttributesByLayout(const gl::Program *program,
+ const std::vector<TranslatedAttribute> &vertexArrayAttribs,
+ const std::vector<TranslatedAttribute> &currentValueAttribs,
+ AttribIndexArray *sortedD3DSemanticsOut,
+ std::vector<const TranslatedAttribute *> *sortedAttributesOut)
+{
+ sortedAttributesOut->clear();
+
+ const auto &locationToSemantic =
+ GetImplAs<ProgramD3D>(program)->getAttribLocationToD3DSemantics();
+
+ for (auto locationIndex : program->getActiveAttribLocationsMask())
+ {
+ int d3dSemantic = locationToSemantic[locationIndex];
+ if (sortedAttributesOut->size() <= static_cast<size_t>(d3dSemantic))
+ {
+ sortedAttributesOut->resize(d3dSemantic + 1);
+ }
+
+ (*sortedD3DSemanticsOut)[d3dSemantic] = d3dSemantic;
+
+ const auto *arrayAttrib = &vertexArrayAttribs[locationIndex];
+ if (arrayAttrib->attribute && arrayAttrib->attribute->enabled)
+ {
+ (*sortedAttributesOut)[d3dSemantic] = arrayAttrib;
+ }
+ else
+ {
+ ASSERT(currentValueAttribs[locationIndex].attribute);
+ (*sortedAttributesOut)[d3dSemantic] = &currentValueAttribs[locationIndex];
+ }
+ }
+}
+
+void UpdateUniformBuffer(ID3D11DeviceContext *deviceContext,
+ UniformStorage11 *storage,
+ const d3d11::Buffer *buffer)
+{
+ deviceContext->UpdateSubresource(buffer->get(), 0, nullptr, storage->getDataPointer(0, 0), 0,
+ 0);
+}
+
} // anonymous namespace
+// StateManager11::SRVCache Implementation.
+
+StateManager11::SRVCache::SRVCache() : mHighestUsedSRV(0)
+{
+}
+
+StateManager11::SRVCache::~SRVCache()
+{
+}
+
void StateManager11::SRVCache::update(size_t resourceIndex, ID3D11ShaderResourceView *srv)
{
ASSERT(resourceIndex < mCurrentSRVs.size());
@@ -128,27 +226,348 @@ void StateManager11::SRVCache::clear()
mHighestUsedSRV = 0;
}
+// ShaderConstants11 implementation
+
+ShaderConstants11::ShaderConstants11()
+ : mVertexDirty(true),
+ mPixelDirty(true),
+ mComputeDirty(true),
+ mSamplerMetadataVSDirty(true),
+ mSamplerMetadataPSDirty(true),
+ mSamplerMetadataCSDirty(true)
+{
+}
+
+ShaderConstants11::~ShaderConstants11()
+{
+}
+
+void ShaderConstants11::init(const gl::Caps &caps)
+{
+ mSamplerMetadataVS.resize(caps.maxVertexTextureImageUnits);
+ mSamplerMetadataPS.resize(caps.maxTextureImageUnits);
+ mSamplerMetadataCS.resize(caps.maxComputeTextureImageUnits);
+}
+
+size_t ShaderConstants11::getRequiredBufferSize(gl::SamplerType samplerType) const
+{
+ switch (samplerType)
+ {
+ case gl::SAMPLER_VERTEX:
+ return sizeof(Vertex) + mSamplerMetadataVS.size() * sizeof(SamplerMetadata);
+ case gl::SAMPLER_PIXEL:
+ return sizeof(Pixel) + mSamplerMetadataPS.size() * sizeof(SamplerMetadata);
+ case gl::SAMPLER_COMPUTE:
+ return sizeof(Compute) + mSamplerMetadataCS.size() * sizeof(SamplerMetadata);
+ default:
+ UNREACHABLE();
+ return 0;
+ }
+}
+
+void ShaderConstants11::markDirty()
+{
+ mVertexDirty = true;
+ mPixelDirty = true;
+ mComputeDirty = true;
+ mSamplerMetadataVSDirty = true;
+ mSamplerMetadataPSDirty = true;
+ mSamplerMetadataCSDirty = true;
+}
+
+bool ShaderConstants11::updateSamplerMetadata(SamplerMetadata *data, const gl::Texture &texture)
+{
+ bool dirty = false;
+ unsigned int baseLevel = texture.getTextureState().getEffectiveBaseLevel();
+ GLenum sizedFormat =
+ texture.getFormat(texture.getTarget(), baseLevel).info->sizedInternalFormat;
+ if (data->baseLevel != static_cast<int>(baseLevel))
+ {
+ data->baseLevel = static_cast<int>(baseLevel);
+ dirty = true;
+ }
+
+ // Some metadata is needed only for integer textures. We avoid updating the constant buffer
+ // unnecessarily by changing the data only in case the texture is an integer texture and
+ // the values have changed.
+ bool needIntegerTextureMetadata = false;
+ // internalFormatBits == 0 means a 32-bit texture in the case of integer textures.
+ int internalFormatBits = 0;
+ switch (sizedFormat)
+ {
+ case GL_RGBA32I:
+ case GL_RGBA32UI:
+ case GL_RGB32I:
+ case GL_RGB32UI:
+ case GL_RG32I:
+ case GL_RG32UI:
+ case GL_R32I:
+ case GL_R32UI:
+ needIntegerTextureMetadata = true;
+ break;
+ case GL_RGBA16I:
+ case GL_RGBA16UI:
+ case GL_RGB16I:
+ case GL_RGB16UI:
+ case GL_RG16I:
+ case GL_RG16UI:
+ case GL_R16I:
+ case GL_R16UI:
+ needIntegerTextureMetadata = true;
+ internalFormatBits = 16;
+ break;
+ case GL_RGBA8I:
+ case GL_RGBA8UI:
+ case GL_RGB8I:
+ case GL_RGB8UI:
+ case GL_RG8I:
+ case GL_RG8UI:
+ case GL_R8I:
+ case GL_R8UI:
+ needIntegerTextureMetadata = true;
+ internalFormatBits = 8;
+ break;
+ case GL_RGB10_A2UI:
+ needIntegerTextureMetadata = true;
+ internalFormatBits = 10;
+ break;
+ default:
+ break;
+ }
+ if (needIntegerTextureMetadata)
+ {
+ if (data->internalFormatBits != internalFormatBits)
+ {
+ data->internalFormatBits = internalFormatBits;
+ dirty = true;
+ }
+ // Pack the wrap values into one integer so we can fit all the metadata in one 4-integer
+ // vector.
+ GLenum wrapS = texture.getWrapS();
+ GLenum wrapT = texture.getWrapT();
+ GLenum wrapR = texture.getWrapR();
+ int wrapModes = GetWrapBits(wrapS) | (GetWrapBits(wrapT) << 2) | (GetWrapBits(wrapR) << 4);
+ if (data->wrapModes != wrapModes)
+ {
+ data->wrapModes = wrapModes;
+ dirty = true;
+ }
+ }
+
+ return dirty;
+}
+
+void ShaderConstants11::setComputeWorkGroups(GLuint numGroupsX,
+ GLuint numGroupsY,
+ GLuint numGroupsZ)
+{
+ mCompute.numWorkGroups[0] = numGroupsX;
+ mCompute.numWorkGroups[1] = numGroupsY;
+ mCompute.numWorkGroups[2] = numGroupsZ;
+ mComputeDirty = true;
+}
+
+void ShaderConstants11::setMultiviewWriteToViewportIndex(GLfloat index)
+{
+ mVertex.multiviewWriteToViewportIndex = index;
+ mVertexDirty = true;
+ mPixel.multiviewWriteToViewportIndex = index;
+ mPixelDirty = true;
+}
+
+void ShaderConstants11::onViewportChange(const gl::Rectangle &glViewport,
+ const D3D11_VIEWPORT &dxViewport,
+ bool is9_3,
+ bool presentPathFast)
+{
+ mVertexDirty = true;
+ mPixelDirty = true;
+
+ // On Feature Level 9_*, we must emulate large and/or negative viewports in the shaders
+ // using viewAdjust (like the D3D9 renderer).
+ if (is9_3)
+ {
+ mVertex.viewAdjust[0] = static_cast<float>((glViewport.width - dxViewport.Width) +
+ 2 * (glViewport.x - dxViewport.TopLeftX)) /
+ dxViewport.Width;
+ mVertex.viewAdjust[1] = static_cast<float>((glViewport.height - dxViewport.Height) +
+ 2 * (glViewport.y - dxViewport.TopLeftY)) /
+ dxViewport.Height;
+ mVertex.viewAdjust[2] = static_cast<float>(glViewport.width) / dxViewport.Width;
+ mVertex.viewAdjust[3] = static_cast<float>(glViewport.height) / dxViewport.Height;
+ }
+
+ mPixel.viewCoords[0] = glViewport.width * 0.5f;
+ mPixel.viewCoords[1] = glViewport.height * 0.5f;
+ mPixel.viewCoords[2] = glViewport.x + (glViewport.width * 0.5f);
+ mPixel.viewCoords[3] = glViewport.y + (glViewport.height * 0.5f);
+
+ // Instanced pointsprite emulation requires ViewCoords to be defined in the
+ // the vertex shader.
+ mVertex.viewCoords[0] = mPixel.viewCoords[0];
+ mVertex.viewCoords[1] = mPixel.viewCoords[1];
+ mVertex.viewCoords[2] = mPixel.viewCoords[2];
+ mVertex.viewCoords[3] = mPixel.viewCoords[3];
+
+ const float zNear = dxViewport.MinDepth;
+ const float zFar = dxViewport.MaxDepth;
+
+ mPixel.depthFront[0] = (zFar - zNear) * 0.5f;
+ mPixel.depthFront[1] = (zNear + zFar) * 0.5f;
+
+ mVertex.depthRange[0] = zNear;
+ mVertex.depthRange[1] = zFar;
+ mVertex.depthRange[2] = zFar - zNear;
+
+ mPixel.depthRange[0] = zNear;
+ mPixel.depthRange[1] = zFar;
+ mPixel.depthRange[2] = zFar - zNear;
+
+ mPixel.viewScale[0] = 1.0f;
+ mPixel.viewScale[1] = presentPathFast ? 1.0f : -1.0f;
+ // Updates to the multiviewWriteToViewportIndex member are to be handled whenever the draw
+ // framebuffer's layout is changed.
+
+ mVertex.viewScale[0] = mPixel.viewScale[0];
+ mVertex.viewScale[1] = mPixel.viewScale[1];
+}
+
+void ShaderConstants11::onSamplerChange(gl::SamplerType samplerType,
+ unsigned int samplerIndex,
+ const gl::Texture &texture)
+{
+ switch (samplerType)
+ {
+ case gl::SAMPLER_VERTEX:
+ if (updateSamplerMetadata(&mSamplerMetadataVS[samplerIndex], texture))
+ {
+ mSamplerMetadataVSDirty = true;
+ }
+ break;
+ case gl::SAMPLER_PIXEL:
+ if (updateSamplerMetadata(&mSamplerMetadataPS[samplerIndex], texture))
+ {
+ mSamplerMetadataPSDirty = true;
+ }
+ break;
+ case gl::SAMPLER_COMPUTE:
+ if (updateSamplerMetadata(&mSamplerMetadataCS[samplerIndex], texture))
+ {
+ mSamplerMetadataCSDirty = true;
+ }
+ break;
+ default:
+ UNREACHABLE();
+ break;
+ }
+}
+
+gl::Error ShaderConstants11::updateBuffer(ID3D11DeviceContext *deviceContext,
+ gl::SamplerType samplerType,
+ const ProgramD3D &programD3D,
+ const d3d11::Buffer &driverConstantBuffer)
+{
+ bool dirty = false;
+ size_t dataSize = 0;
+ const uint8_t *data = nullptr;
+ const uint8_t *samplerData = nullptr;
+
+ switch (samplerType)
+ {
+ case gl::SAMPLER_VERTEX:
+ dirty = mVertexDirty || mSamplerMetadataVSDirty;
+ dataSize = sizeof(Vertex);
+ data = reinterpret_cast<const uint8_t *>(&mVertex);
+ samplerData = reinterpret_cast<const uint8_t *>(mSamplerMetadataVS.data());
+ mVertexDirty = false;
+ mSamplerMetadataVSDirty = false;
+ break;
+ case gl::SAMPLER_PIXEL:
+ dirty = mPixelDirty || mSamplerMetadataPSDirty;
+ dataSize = sizeof(Pixel);
+ data = reinterpret_cast<const uint8_t *>(&mPixel);
+ samplerData = reinterpret_cast<const uint8_t *>(mSamplerMetadataPS.data());
+ mPixelDirty = false;
+ mSamplerMetadataPSDirty = false;
+ break;
+ case gl::SAMPLER_COMPUTE:
+ dirty = mComputeDirty || mSamplerMetadataCSDirty;
+ dataSize = sizeof(Compute);
+ data = reinterpret_cast<const uint8_t *>(&mCompute);
+ samplerData = reinterpret_cast<const uint8_t *>(mSamplerMetadataCS.data());
+ mComputeDirty = false;
+ mSamplerMetadataCSDirty = false;
+ break;
+ default:
+ UNREACHABLE();
+ break;
+ }
+
+ ASSERT(driverConstantBuffer.valid());
+
+ if (!dirty)
+ {
+ return gl::NoError();
+ }
+
+ // Previous buffer contents are discarded, so we need to refresh the whole buffer.
+ D3D11_MAPPED_SUBRESOURCE mapping = {0};
+ HRESULT result =
+ deviceContext->Map(driverConstantBuffer.get(), 0, D3D11_MAP_WRITE_DISCARD, 0, &mapping);
+
+ if (FAILED(result))
+ {
+ return gl::OutOfMemory() << "Internal error mapping constant buffer: " << gl::FmtHR(result);
+ }
+
+ size_t samplerDataBytes = sizeof(SamplerMetadata) * programD3D.getUsedSamplerRange(samplerType);
+
+ memcpy(mapping.pData, data, dataSize);
+ memcpy(reinterpret_cast<uint8_t *>(mapping.pData) + dataSize, samplerData, samplerDataBytes);
+
+ deviceContext->Unmap(driverConstantBuffer.get(), 0);
+
+ return gl::NoError();
+}
+
+static const GLenum QueryTypes[] = {GL_ANY_SAMPLES_PASSED, GL_ANY_SAMPLES_PASSED_CONSERVATIVE,
+ GL_TRANSFORM_FEEDBACK_PRIMITIVES_WRITTEN, GL_TIME_ELAPSED_EXT,
+ GL_COMMANDS_COMPLETED_CHROMIUM};
+
StateManager11::StateManager11(Renderer11 *renderer)
: mRenderer(renderer),
- mBlendStateIsDirty(false),
+ mInternalDirtyBits(),
mCurBlendColor(0, 0, 0, 0),
mCurSampleMask(0),
- mDepthStencilStateIsDirty(false),
mCurStencilRef(0),
mCurStencilBackRef(0),
mCurStencilSize(0),
- mRasterizerStateIsDirty(false),
- mScissorStateIsDirty(false),
mCurScissorEnabled(false),
mCurScissorRect(),
- mViewportStateIsDirty(false),
mCurViewport(),
mCurNear(0.0f),
mCurFar(0.0f),
mViewportBounds(),
+ mRenderTargetIsDirty(true),
mCurPresentPathFastEnabled(false),
mCurPresentPathFastColorBufferHeight(0),
- mAppliedDSV(angle::DirtyPointer)
+ mDirtyCurrentValueAttribs(),
+ mCurrentValueAttribs(),
+ mCurrentInputLayout(),
+ mInputLayoutIsDirty(false),
+ mVertexAttribsNeedTranslation(false),
+ mDirtyVertexBufferRange(gl::MAX_VERTEX_ATTRIBS, 0),
+ mCurrentPrimitiveTopology(D3D_PRIMITIVE_TOPOLOGY_UNDEFINED),
+ mDirtySwizzles(false),
+ mAppliedIB(nullptr),
+ mAppliedIBFormat(DXGI_FORMAT_UNKNOWN),
+ mAppliedIBOffset(0),
+ mIndexBufferIsDirty(false),
+ mVertexDataManager(renderer),
+ mIndexDataManager(renderer),
+ mIsMultiviewEnabled(false),
+ mEmptySerial(mRenderer->generateSerial()),
+ mIsTransformFeedbackCurrentlyActiveUnpaused(false)
{
mCurBlendState.blend = false;
mCurBlendState.sourceBlendRGB = GL_ONE;
@@ -182,64 +601,127 @@ StateManager11::StateManager11(Renderer11 *renderer)
mCurRasterState.rasterizerDiscard = false;
mCurRasterState.cullFace = false;
- mCurRasterState.cullMode = GL_BACK;
+ mCurRasterState.cullMode = gl::CullFaceMode::Back;
mCurRasterState.frontFace = GL_CCW;
mCurRasterState.polygonOffsetFill = false;
mCurRasterState.polygonOffsetFactor = 0.0f;
mCurRasterState.polygonOffsetUnits = 0.0f;
mCurRasterState.pointDrawMode = false;
mCurRasterState.multiSample = false;
+
+ // Start with all internal dirty bits set.
+ mInternalDirtyBits.set();
+
+ // Initially all current value attributes must be updated on first use.
+ mDirtyCurrentValueAttribs.set();
+
+ mCurrentVertexBuffers.fill(nullptr);
+ mCurrentVertexStrides.fill(std::numeric_limits<UINT>::max());
+ mCurrentVertexOffsets.fill(std::numeric_limits<UINT>::max());
}
StateManager11::~StateManager11()
{
}
-void StateManager11::updateStencilSizeIfChanged(bool depthStencilInitialized,
- unsigned int stencilSize)
+template <typename SRVType>
+void StateManager11::setShaderResourceInternal(gl::SamplerType shaderType,
+ UINT resourceSlot,
+ const SRVType *srv)
{
- if (!depthStencilInitialized || stencilSize != mCurStencilSize)
+ auto &currentSRVs = (shaderType == gl::SAMPLER_VERTEX ? mCurVertexSRVs : mCurPixelSRVs);
+
+ ASSERT(static_cast<size_t>(resourceSlot) < currentSRVs.size());
+ const SRVRecord &record = currentSRVs[resourceSlot];
+
+ if (record.srv != reinterpret_cast<uintptr_t>(srv))
{
- mCurStencilSize = stencilSize;
- mDepthStencilStateIsDirty = true;
+ ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
+ ID3D11ShaderResourceView *srvPtr = srv ? srv->get() : nullptr;
+ if (shaderType == gl::SAMPLER_VERTEX)
+ {
+ deviceContext->VSSetShaderResources(resourceSlot, 1, &srvPtr);
+ }
+ else
+ {
+ deviceContext->PSSetShaderResources(resourceSlot, 1, &srvPtr);
+ }
+
+ currentSRVs.update(resourceSlot, srvPtr);
}
}
-void StateManager11::setViewportBounds(const int width, const int height)
+void StateManager11::updateStencilSizeIfChanged(bool depthStencilInitialized,
+ unsigned int stencilSize)
{
- if (mRenderer->getRenderer11DeviceCaps().featureLevel <= D3D_FEATURE_LEVEL_9_3 &&
- (mViewportBounds.width != width || mViewportBounds.height != height))
+ if (!depthStencilInitialized || stencilSize != mCurStencilSize)
{
- mViewportBounds = gl::Extents(width, height, 1);
- mViewportStateIsDirty = true;
+ mCurStencilSize = stencilSize;
+ mInternalDirtyBits.set(DIRTY_BIT_DEPTH_STENCIL_STATE);
}
}
-void StateManager11::updatePresentPath(bool presentPathFastActive,
- const gl::FramebufferAttachment *framebufferAttachment)
+void StateManager11::checkPresentPath(const gl::Context *context)
{
- const int colorBufferHeight =
- framebufferAttachment ? framebufferAttachment->getSize().height : 0;
+ if (!mRenderer->presentPathFastEnabled())
+ return;
+
+ const auto *framebuffer = context->getGLState().getDrawFramebuffer();
+ const auto *firstColorAttachment = framebuffer->getFirstColorbuffer();
+ const bool presentPathFastActive = UsePresentPathFast(mRenderer, firstColorAttachment);
+
+ const int colorBufferHeight = firstColorAttachment ? firstColorAttachment->getSize().height : 0;
if ((mCurPresentPathFastEnabled != presentPathFastActive) ||
(presentPathFastActive && (colorBufferHeight != mCurPresentPathFastColorBufferHeight)))
{
mCurPresentPathFastEnabled = presentPathFastActive;
mCurPresentPathFastColorBufferHeight = colorBufferHeight;
- mViewportStateIsDirty = true; // Viewport may need to be vertically inverted
- mScissorStateIsDirty = true; // Scissor rect may need to be vertically inverted
- mRasterizerStateIsDirty = true; // Cull Mode may need to be inverted
+
+ // Scissor rect may need to be vertically inverted
+ mInternalDirtyBits.set(DIRTY_BIT_SCISSOR_STATE);
+
+ // Cull Mode may need to be inverted
+ mInternalDirtyBits.set(DIRTY_BIT_RASTERIZER_STATE);
+
+ // Viewport may need to be vertically inverted
+ invalidateViewport(context);
}
}
-void StateManager11::syncState(const gl::State &state, const gl::State::DirtyBits &dirtyBits)
+gl::Error StateManager11::updateStateForCompute(const gl::Context *context,
+ GLuint numGroupsX,
+ GLuint numGroupsY,
+ GLuint numGroupsZ)
+{
+ mShaderConstants.setComputeWorkGroups(numGroupsX, numGroupsY, numGroupsZ);
+
+ // TODO(jmadill): Use dirty bits.
+ const auto &glState = context->getGLState();
+ auto *programD3D = GetImplAs<ProgramD3D>(glState.getProgram());
+ programD3D->updateSamplerMapping();
+
+ // TODO(jmadill): Use dirty bits.
+ ANGLE_TRY(generateSwizzlesForShader(context, gl::SAMPLER_COMPUTE));
+
+ // TODO(jmadill): More complete implementation.
+ ANGLE_TRY(syncTextures(context));
+
+ // TODO(Xinghua): applyUniformBuffers for compute shader.
+
+ return gl::NoError();
+}
+
+void StateManager11::syncState(const gl::Context *context, const gl::State::DirtyBits &dirtyBits)
{
if (!dirtyBits.any())
{
return;
}
- for (unsigned int dirtyBit : angle::IterateBitSet(dirtyBits))
+ const auto &state = context->getGLState();
+
+ for (auto dirtyBit : dirtyBits)
{
switch (dirtyBit)
{
@@ -249,7 +731,7 @@ void StateManager11::syncState(const gl::State &state, const gl::State::DirtyBit
if (blendState.blendEquationRGB != mCurBlendState.blendEquationRGB ||
blendState.blendEquationAlpha != mCurBlendState.blendEquationAlpha)
{
- mBlendStateIsDirty = true;
+ mInternalDirtyBits.set(DIRTY_BIT_BLEND_STATE);
}
break;
}
@@ -261,27 +743,27 @@ void StateManager11::syncState(const gl::State &state, const gl::State::DirtyBit
blendState.sourceBlendAlpha != mCurBlendState.sourceBlendAlpha ||
blendState.destBlendAlpha != mCurBlendState.destBlendAlpha)
{
- mBlendStateIsDirty = true;
+ mInternalDirtyBits.set(DIRTY_BIT_BLEND_STATE);
}
break;
}
case gl::State::DIRTY_BIT_BLEND_ENABLED:
if (state.getBlendState().blend != mCurBlendState.blend)
{
- mBlendStateIsDirty = true;
+ mInternalDirtyBits.set(DIRTY_BIT_BLEND_STATE);
}
break;
case gl::State::DIRTY_BIT_SAMPLE_ALPHA_TO_COVERAGE_ENABLED:
if (state.getBlendState().sampleAlphaToCoverage !=
mCurBlendState.sampleAlphaToCoverage)
{
- mBlendStateIsDirty = true;
+ mInternalDirtyBits.set(DIRTY_BIT_BLEND_STATE);
}
break;
case gl::State::DIRTY_BIT_DITHER_ENABLED:
if (state.getBlendState().dither != mCurBlendState.dither)
{
- mBlendStateIsDirty = true;
+ mInternalDirtyBits.set(DIRTY_BIT_BLEND_STATE);
}
break;
case gl::State::DIRTY_BIT_COLOR_MASK:
@@ -292,38 +774,38 @@ void StateManager11::syncState(const gl::State &state, const gl::State::DirtyBit
blendState.colorMaskBlue != mCurBlendState.colorMaskBlue ||
blendState.colorMaskAlpha != mCurBlendState.colorMaskAlpha)
{
- mBlendStateIsDirty = true;
+ mInternalDirtyBits.set(DIRTY_BIT_BLEND_STATE);
}
break;
}
case gl::State::DIRTY_BIT_BLEND_COLOR:
if (state.getBlendColor() != mCurBlendColor)
{
- mBlendStateIsDirty = true;
+ mInternalDirtyBits.set(DIRTY_BIT_BLEND_STATE);
}
break;
case gl::State::DIRTY_BIT_DEPTH_MASK:
if (state.getDepthStencilState().depthMask != mCurDepthStencilState.depthMask)
{
- mDepthStencilStateIsDirty = true;
+ mInternalDirtyBits.set(DIRTY_BIT_DEPTH_STENCIL_STATE);
}
break;
case gl::State::DIRTY_BIT_DEPTH_TEST_ENABLED:
if (state.getDepthStencilState().depthTest != mCurDepthStencilState.depthTest)
{
- mDepthStencilStateIsDirty = true;
+ mInternalDirtyBits.set(DIRTY_BIT_DEPTH_STENCIL_STATE);
}
break;
case gl::State::DIRTY_BIT_DEPTH_FUNC:
if (state.getDepthStencilState().depthFunc != mCurDepthStencilState.depthFunc)
{
- mDepthStencilStateIsDirty = true;
+ mInternalDirtyBits.set(DIRTY_BIT_DEPTH_STENCIL_STATE);
}
break;
case gl::State::DIRTY_BIT_STENCIL_TEST_ENABLED:
if (state.getDepthStencilState().stencilTest != mCurDepthStencilState.stencilTest)
{
- mDepthStencilStateIsDirty = true;
+ mInternalDirtyBits.set(DIRTY_BIT_DEPTH_STENCIL_STATE);
}
break;
case gl::State::DIRTY_BIT_STENCIL_FUNCS_FRONT:
@@ -333,7 +815,7 @@ void StateManager11::syncState(const gl::State &state, const gl::State::DirtyBit
depthStencil.stencilMask != mCurDepthStencilState.stencilMask ||
state.getStencilRef() != mCurStencilRef)
{
- mDepthStencilStateIsDirty = true;
+ mInternalDirtyBits.set(DIRTY_BIT_DEPTH_STENCIL_STATE);
}
break;
}
@@ -344,7 +826,7 @@ void StateManager11::syncState(const gl::State &state, const gl::State::DirtyBit
depthStencil.stencilBackMask != mCurDepthStencilState.stencilBackMask ||
state.getStencilBackRef() != mCurStencilBackRef)
{
- mDepthStencilStateIsDirty = true;
+ mInternalDirtyBits.set(DIRTY_BIT_DEPTH_STENCIL_STATE);
}
break;
}
@@ -352,14 +834,14 @@ void StateManager11::syncState(const gl::State &state, const gl::State::DirtyBit
if (state.getDepthStencilState().stencilWritemask !=
mCurDepthStencilState.stencilWritemask)
{
- mDepthStencilStateIsDirty = true;
+ mInternalDirtyBits.set(DIRTY_BIT_DEPTH_STENCIL_STATE);
}
break;
case gl::State::DIRTY_BIT_STENCIL_WRITEMASK_BACK:
if (state.getDepthStencilState().stencilBackWritemask !=
mCurDepthStencilState.stencilBackWritemask)
{
- mDepthStencilStateIsDirty = true;
+ mInternalDirtyBits.set(DIRTY_BIT_DEPTH_STENCIL_STATE);
}
break;
case gl::State::DIRTY_BIT_STENCIL_OPS_FRONT:
@@ -370,7 +852,7 @@ void StateManager11::syncState(const gl::State &state, const gl::State::DirtyBit
mCurDepthStencilState.stencilPassDepthFail ||
depthStencil.stencilPassDepthPass != mCurDepthStencilState.stencilPassDepthPass)
{
- mDepthStencilStateIsDirty = true;
+ mInternalDirtyBits.set(DIRTY_BIT_DEPTH_STENCIL_STATE);
}
break;
}
@@ -383,33 +865,33 @@ void StateManager11::syncState(const gl::State &state, const gl::State::DirtyBit
depthStencil.stencilBackPassDepthPass !=
mCurDepthStencilState.stencilBackPassDepthPass)
{
- mDepthStencilStateIsDirty = true;
+ mInternalDirtyBits.set(DIRTY_BIT_DEPTH_STENCIL_STATE);
}
break;
}
case gl::State::DIRTY_BIT_CULL_FACE_ENABLED:
if (state.getRasterizerState().cullFace != mCurRasterState.cullFace)
{
- mRasterizerStateIsDirty = true;
+ mInternalDirtyBits.set(DIRTY_BIT_RASTERIZER_STATE);
}
break;
case gl::State::DIRTY_BIT_CULL_FACE:
if (state.getRasterizerState().cullMode != mCurRasterState.cullMode)
{
- mRasterizerStateIsDirty = true;
+ mInternalDirtyBits.set(DIRTY_BIT_RASTERIZER_STATE);
}
break;
case gl::State::DIRTY_BIT_FRONT_FACE:
if (state.getRasterizerState().frontFace != mCurRasterState.frontFace)
{
- mRasterizerStateIsDirty = true;
+ mInternalDirtyBits.set(DIRTY_BIT_RASTERIZER_STATE);
}
break;
case gl::State::DIRTY_BIT_POLYGON_OFFSET_FILL_ENABLED:
if (state.getRasterizerState().polygonOffsetFill !=
mCurRasterState.polygonOffsetFill)
{
- mRasterizerStateIsDirty = true;
+ mInternalDirtyBits.set(DIRTY_BIT_RASTERIZER_STATE);
}
break;
case gl::State::DIRTY_BIT_POLYGON_OFFSET:
@@ -418,7 +900,7 @@ void StateManager11::syncState(const gl::State &state, const gl::State::DirtyBit
if (rasterState.polygonOffsetFactor != mCurRasterState.polygonOffsetFactor ||
rasterState.polygonOffsetUnits != mCurRasterState.polygonOffsetUnits)
{
- mRasterizerStateIsDirty = true;
+ mInternalDirtyBits.set(DIRTY_BIT_RASTERIZER_STATE);
}
break;
}
@@ -426,58 +908,150 @@ void StateManager11::syncState(const gl::State &state, const gl::State::DirtyBit
if (state.getRasterizerState().rasterizerDiscard !=
mCurRasterState.rasterizerDiscard)
{
- mRasterizerStateIsDirty = true;
+ mInternalDirtyBits.set(DIRTY_BIT_RASTERIZER_STATE);
+
+ // Enabling/disabling rasterizer discard affects the pixel shader.
+ invalidateShaders();
}
break;
case gl::State::DIRTY_BIT_SCISSOR:
if (state.getScissor() != mCurScissorRect)
{
- mScissorStateIsDirty = true;
+ mInternalDirtyBits.set(DIRTY_BIT_SCISSOR_STATE);
}
break;
case gl::State::DIRTY_BIT_SCISSOR_TEST_ENABLED:
if (state.isScissorTestEnabled() != mCurScissorEnabled)
{
- mScissorStateIsDirty = true;
+ mInternalDirtyBits.set(DIRTY_BIT_SCISSOR_STATE);
// Rasterizer state update needs mCurScissorsEnabled and updates when it changes
- mRasterizerStateIsDirty = true;
+ mInternalDirtyBits.set(DIRTY_BIT_RASTERIZER_STATE);
}
break;
case gl::State::DIRTY_BIT_DEPTH_RANGE:
if (state.getNearPlane() != mCurNear || state.getFarPlane() != mCurFar)
{
- mViewportStateIsDirty = true;
+ invalidateViewport(context);
}
break;
case gl::State::DIRTY_BIT_VIEWPORT:
if (state.getViewport() != mCurViewport)
{
- mViewportStateIsDirty = true;
+ invalidateViewport(context);
+ }
+ break;
+ case gl::State::DIRTY_BIT_DRAW_FRAMEBUFFER_BINDING:
+ invalidateRenderTarget();
+ if (mIsMultiviewEnabled)
+ {
+ handleMultiviewDrawFramebufferChange(context);
}
break;
+ case gl::State::DIRTY_BIT_VERTEX_ARRAY_BINDING:
+ invalidateVertexBuffer();
+ // Force invalidate the current value attributes, since the VertexArray11 keeps an
+ // internal cache of TranslatedAttributes, and they CurrentValue attributes are
+ // owned by the StateManager11/Context.
+ mDirtyCurrentValueAttribs.set();
+ // Invalidate the cached index buffer.
+ mIndexBufferIsDirty = true;
+ break;
+ case gl::State::DIRTY_BIT_TEXTURE_BINDINGS:
+ invalidateTexturesAndSamplers();
+ break;
+ case gl::State::DIRTY_BIT_SAMPLER_BINDINGS:
+ invalidateTexturesAndSamplers();
+ break;
+ case gl::State::DIRTY_BIT_PROGRAM_EXECUTABLE:
+ {
+ mInternalDirtyBits.set(DIRTY_BIT_SHADERS);
+ invalidateVertexBuffer();
+ invalidateRenderTarget();
+ invalidateTexturesAndSamplers();
+ invalidateProgramUniforms();
+ invalidateProgramUniformBuffers();
+ gl::VertexArray *vao = state.getVertexArray();
+ if (mIsMultiviewEnabled && vao != nullptr)
+ {
+ // If ANGLE_multiview is enabled, the attribute divisor has to be updated for
+ // each binding.
+ VertexArray11 *vao11 = GetImplAs<VertexArray11>(vao);
+ const gl::Program *program = state.getProgram();
+ int numViews = 1;
+ if (program != nullptr && program->usesMultiview())
+ {
+ numViews = program->getNumViews();
+ }
+ vao11->markAllAttributeDivisorsForAdjustment(numViews);
+ }
+ break;
+ }
+ case gl::State::DIRTY_BIT_CURRENT_VALUES:
+ {
+ for (auto attribIndex : state.getAndResetDirtyCurrentValues())
+ {
+ invalidateCurrentValueAttrib(attribIndex);
+ }
+ }
default:
break;
}
}
+
+ // TODO(jmadill): Input layout and vertex buffer state.
}
-gl::Error StateManager11::setBlendState(const gl::Framebuffer *framebuffer,
- const gl::BlendState &blendState,
- const gl::ColorF &blendColor,
- unsigned int sampleMask)
+void StateManager11::handleMultiviewDrawFramebufferChange(const gl::Context *context)
{
- if (!mBlendStateIsDirty && sampleMask == mCurSampleMask)
+ const auto &glState = context->getGLState();
+ const gl::Framebuffer *drawFramebuffer = glState.getDrawFramebuffer();
+ ASSERT(drawFramebuffer != nullptr);
+
+ // Update viewport offsets.
+ const std::vector<gl::Offset> *attachmentViewportOffsets =
+ drawFramebuffer->getViewportOffsets();
+ const std::vector<gl::Offset> &viewportOffsets =
+ attachmentViewportOffsets != nullptr
+ ? *attachmentViewportOffsets
+ : gl::FramebufferAttachment::GetDefaultViewportOffsetVector();
+ if (mViewportOffsets != viewportOffsets)
{
- return gl::Error(GL_NO_ERROR);
- }
+ mViewportOffsets = viewportOffsets;
- ID3D11BlendState *dxBlendState = nullptr;
- gl::Error error =
- mRenderer->getStateCache().getBlendState(framebuffer, blendState, &dxBlendState);
- if (error.isError())
+ // Because new viewport offsets are to be applied, we have to mark the internal viewport and
+ // scissor state as dirty.
+ invalidateViewport(context);
+ mInternalDirtyBits.set(DIRTY_BIT_SCISSOR_STATE);
+ }
+ switch (drawFramebuffer->getMultiviewLayout())
{
- return error;
+ case GL_FRAMEBUFFER_MULTIVIEW_SIDE_BY_SIDE_ANGLE:
+ mShaderConstants.setMultiviewWriteToViewportIndex(1.0f);
+ break;
+ case GL_FRAMEBUFFER_MULTIVIEW_LAYERED_ANGLE:
+ // Because the base view index is applied as an offset to the 2D texture array when the
+ // RTV is created, we just have to pass a boolean to select which code path is to be
+ // used.
+ mShaderConstants.setMultiviewWriteToViewportIndex(0.0f);
+ break;
+ default:
+ // There is no need to update the value in the constant buffer if the active framebuffer
+ // object does not have a multiview layout.
+ break;
}
+}
+
+gl::Error StateManager11::syncBlendState(const gl::Context *context,
+ const gl::Framebuffer *framebuffer,
+ const gl::BlendState &blendState,
+ const gl::ColorF &blendColor,
+ unsigned int sampleMask)
+{
+ const d3d11::BlendState *dxBlendState = nullptr;
+ const d3d11::BlendStateKey &key =
+ RenderStateCache::GetBlendStateKey(context, framebuffer, blendState);
+
+ ANGLE_TRY(mRenderer->getBlendState(key, &dxBlendState));
ASSERT(dxBlendState != nullptr);
@@ -500,62 +1074,53 @@ gl::Error StateManager11::setBlendState(const gl::Framebuffer *framebuffer,
blendColors[3] = blendColor.alpha;
}
- mRenderer->getDeviceContext()->OMSetBlendState(dxBlendState, blendColors, sampleMask);
+ mRenderer->getDeviceContext()->OMSetBlendState(dxBlendState->get(), blendColors, sampleMask);
mCurBlendState = blendState;
mCurBlendColor = blendColor;
mCurSampleMask = sampleMask;
- mBlendStateIsDirty = false;
-
- return error;
+ return gl::NoError();
}
-gl::Error StateManager11::setDepthStencilState(const gl::State &glState)
+gl::Error StateManager11::syncDepthStencilState(const gl::State &glState)
{
- const auto &fbo = *glState.getDrawFramebuffer();
-
- // Disable the depth test/depth write if we are using a stencil-only attachment.
- // This is because ANGLE emulates stencil-only with D24S8 on D3D11 - we should neither read
- // nor write to the unused depth part of this emulated texture.
- bool disableDepth = (!fbo.hasDepth() && fbo.hasStencil());
-
- // Similarly we disable the stencil portion of the DS attachment if the app only binds depth.
- bool disableStencil = (fbo.hasDepth() && !fbo.hasStencil());
+ mCurDepthStencilState = glState.getDepthStencilState();
+ mCurStencilRef = glState.getStencilRef();
+ mCurStencilBackRef = glState.getStencilBackRef();
- // CurDisableDepth/Stencil are reset automatically after we call forceSetDepthStencilState.
- if (!mDepthStencilStateIsDirty && mCurDisableDepth.valid() &&
- disableDepth == mCurDisableDepth.value() && mCurDisableStencil.valid() &&
- disableStencil == mCurDisableStencil.value())
+ // get the maximum size of the stencil ref
+ unsigned int maxStencil = 0;
+ if (mCurDepthStencilState.stencilTest && mCurStencilSize > 0)
{
- return gl::Error(GL_NO_ERROR);
+ maxStencil = (1 << mCurStencilSize) - 1;
}
+ ASSERT((mCurDepthStencilState.stencilWritemask & maxStencil) ==
+ (mCurDepthStencilState.stencilBackWritemask & maxStencil));
+ ASSERT(mCurStencilRef == mCurStencilBackRef);
+ ASSERT((mCurDepthStencilState.stencilMask & maxStencil) ==
+ (mCurDepthStencilState.stencilBackMask & maxStencil));
- const auto &depthStencilState = glState.getDepthStencilState();
- int stencilRef = glState.getStencilRef();
- int stencilBackRef = glState.getStencilBackRef();
+ gl::DepthStencilState modifiedGLState = glState.getDepthStencilState();
- // get the maximum size of the stencil ref
- unsigned int maxStencil = 0;
- if (depthStencilState.stencilTest && mCurStencilSize > 0)
+ ASSERT(mCurDisableDepth.valid() && mCurDisableStencil.valid());
+
+ if (mCurDisableDepth.value())
{
- maxStencil = (1 << mCurStencilSize) - 1;
+ modifiedGLState.depthTest = false;
+ modifiedGLState.depthMask = false;
}
- ASSERT((depthStencilState.stencilWritemask & maxStencil) ==
- (depthStencilState.stencilBackWritemask & maxStencil));
- ASSERT(stencilRef == stencilBackRef);
- ASSERT((depthStencilState.stencilMask & maxStencil) ==
- (depthStencilState.stencilBackMask & maxStencil));
- ID3D11DepthStencilState *dxDepthStencilState = NULL;
- gl::Error error = mRenderer->getStateCache().getDepthStencilState(
- depthStencilState, disableDepth, disableStencil, &dxDepthStencilState);
- if (error.isError())
+ if (mCurDisableStencil.value())
{
- return error;
+ modifiedGLState.stencilWritemask = 0;
+ modifiedGLState.stencilBackWritemask = 0;
+ modifiedGLState.stencilTest = false;
}
- ASSERT(dxDepthStencilState);
+ const d3d11::DepthStencilState *d3dState = nullptr;
+ ANGLE_TRY(mRenderer->getDepthStencilState(modifiedGLState, &d3dState));
+ ASSERT(d3dState);
// Max D3D11 stencil reference value is 0xFF,
// corresponding to the max 8 bits in a stencil buffer
@@ -565,30 +1130,21 @@ gl::Error StateManager11::setDepthStencilState(const gl::State &glState)
"Unexpected value of D3D11_DEFAULT_STENCIL_READ_MASK");
static_assert(D3D11_DEFAULT_STENCIL_WRITE_MASK == 0xFF,
"Unexpected value of D3D11_DEFAULT_STENCIL_WRITE_MASK");
- UINT dxStencilRef = std::min<UINT>(stencilRef, 0xFFu);
+ UINT dxStencilRef = std::min<UINT>(mCurStencilRef, 0xFFu);
- mRenderer->getDeviceContext()->OMSetDepthStencilState(dxDepthStencilState, dxStencilRef);
+ mRenderer->getDeviceContext()->OMSetDepthStencilState(d3dState->get(), dxStencilRef);
- mCurDepthStencilState = depthStencilState;
- mCurStencilRef = stencilRef;
- mCurStencilBackRef = stencilBackRef;
- mCurDisableDepth = disableDepth;
- mCurDisableStencil = disableStencil;
-
- mDepthStencilStateIsDirty = false;
-
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error StateManager11::setRasterizerState(const gl::RasterizerState &rasterState)
+gl::Error StateManager11::syncRasterizerState(const gl::Context *context, bool pointDrawMode)
{
- if (!mRasterizerStateIsDirty)
- {
- return gl::Error(GL_NO_ERROR);
- }
+ // TODO: Remove pointDrawMode and multiSample from gl::RasterizerState.
+ gl::RasterizerState rasterState = context->getGLState().getRasterizerState();
+ rasterState.pointDrawMode = pointDrawMode;
+ rasterState.multiSample = mCurRasterState.multiSample;
ID3D11RasterizerState *dxRasterState = nullptr;
- gl::Error error(GL_NO_ERROR);
if (mCurPresentPathFastEnabled)
{
@@ -607,33 +1163,23 @@ gl::Error StateManager11::setRasterizerState(const gl::RasterizerState &rasterSt
modifiedRasterState.frontFace = GL_CCW;
}
- error = mRenderer->getStateCache().getRasterizerState(modifiedRasterState,
- mCurScissorEnabled, &dxRasterState);
+ ANGLE_TRY(
+ mRenderer->getRasterizerState(modifiedRasterState, mCurScissorEnabled, &dxRasterState));
}
else
{
- error = mRenderer->getStateCache().getRasterizerState(rasterState, mCurScissorEnabled,
- &dxRasterState);
- }
-
- if (error.isError())
- {
- return error;
+ ANGLE_TRY(mRenderer->getRasterizerState(rasterState, mCurScissorEnabled, &dxRasterState));
}
mRenderer->getDeviceContext()->RSSetState(dxRasterState);
- mCurRasterState = rasterState;
- mRasterizerStateIsDirty = false;
+ mCurRasterState = rasterState;
- return error;
+ return gl::NoError();
}
-void StateManager11::setScissorRectangle(const gl::Rectangle &scissor, bool enabled)
+void StateManager11::syncScissorRectangle(const gl::Rectangle &scissor, bool enabled)
{
- if (!mScissorStateIsDirty)
- return;
-
int modifiedScissorY = scissor.y;
if (mCurPresentPathFastEnabled)
{
@@ -642,37 +1188,41 @@ void StateManager11::setScissorRectangle(const gl::Rectangle &scissor, bool enab
if (enabled)
{
- D3D11_RECT rect;
- rect.left = std::max(0, scissor.x);
- rect.top = std::max(0, modifiedScissorY);
- rect.right = scissor.x + std::max(0, scissor.width);
- rect.bottom = modifiedScissorY + std::max(0, scissor.height);
-
- mRenderer->getDeviceContext()->RSSetScissorRects(1, &rect);
+ std::array<D3D11_RECT, gl::IMPLEMENTATION_ANGLE_MULTIVIEW_MAX_VIEWS> rectangles;
+ const UINT numRectangles = static_cast<UINT>(mViewportOffsets.size());
+ for (UINT i = 0u; i < numRectangles; ++i)
+ {
+ D3D11_RECT &rect = rectangles[i];
+ int x = scissor.x + mViewportOffsets[i].x;
+ int y = modifiedScissorY + mViewportOffsets[i].y;
+ rect.left = std::max(0, x);
+ rect.top = std::max(0, y);
+ rect.right = x + std::max(0, scissor.width);
+ rect.bottom = y + std::max(0, scissor.height);
+ }
+ mRenderer->getDeviceContext()->RSSetScissorRects(numRectangles, rectangles.data());
}
mCurScissorRect = scissor;
mCurScissorEnabled = enabled;
- mScissorStateIsDirty = false;
}
-void StateManager11::setViewport(const gl::Caps *caps,
- const gl::Rectangle &viewport,
- float zNear,
- float zFar)
+void StateManager11::syncViewport(const gl::Context *context)
{
- if (!mViewportStateIsDirty)
- return;
-
- float actualZNear = gl::clamp01(zNear);
- float actualZFar = gl::clamp01(zFar);
-
- int dxMaxViewportBoundsX = static_cast<int>(caps->maxViewportWidth);
- int dxMaxViewportBoundsY = static_cast<int>(caps->maxViewportHeight);
+ const auto &glState = context->getGLState();
+ gl::Framebuffer *framebuffer = glState.getDrawFramebuffer();
+ float actualZNear = gl::clamp01(glState.getNearPlane());
+ float actualZFar = gl::clamp01(glState.getFarPlane());
+
+ const auto &caps = context->getCaps();
+ int dxMaxViewportBoundsX = static_cast<int>(caps.maxViewportWidth);
+ int dxMaxViewportBoundsY = static_cast<int>(caps.maxViewportHeight);
int dxMinViewportBoundsX = -dxMaxViewportBoundsX;
int dxMinViewportBoundsY = -dxMaxViewportBoundsY;
- if (mRenderer->getRenderer11DeviceCaps().featureLevel <= D3D_FEATURE_LEVEL_9_3)
+ bool is9_3 = mRenderer->getRenderer11DeviceCaps().featureLevel <= D3D_FEATURE_LEVEL_9_3;
+
+ if (is9_3)
{
// Feature Level 9 viewports shouldn't exceed the dimensions of the rendertarget.
dxMaxViewportBoundsX = static_cast<int>(mViewportBounds.width);
@@ -681,173 +1231,295 @@ void StateManager11::setViewport(const gl::Caps *caps,
dxMinViewportBoundsY = 0;
}
- int dxViewportTopLeftX = gl::clamp(viewport.x, dxMinViewportBoundsX, dxMaxViewportBoundsX);
- int dxViewportTopLeftY = gl::clamp(viewport.y, dxMinViewportBoundsY, dxMaxViewportBoundsY);
- int dxViewportWidth = gl::clamp(viewport.width, 0, dxMaxViewportBoundsX - dxViewportTopLeftX);
- int dxViewportHeight = gl::clamp(viewport.height, 0, dxMaxViewportBoundsY - dxViewportTopLeftY);
+ const auto &viewport = glState.getViewport();
+ std::array<D3D11_VIEWPORT, gl::IMPLEMENTATION_ANGLE_MULTIVIEW_MAX_VIEWS> dxViewports;
+ const UINT numRectangles = static_cast<UINT>(mViewportOffsets.size());
- D3D11_VIEWPORT dxViewport;
- dxViewport.TopLeftX = static_cast<float>(dxViewportTopLeftX);
+ int dxViewportTopLeftX = 0;
+ int dxViewportTopLeftY = 0;
+ int dxViewportWidth = 0;
+ int dxViewportHeight = 0;
- if (mCurPresentPathFastEnabled)
- {
- // When present path fast is active and we're rendering to framebuffer 0, we must invert
- // the viewport in Y-axis.
- // NOTE: We delay the inversion until right before the call to RSSetViewports, and leave
- // dxViewportTopLeftY unchanged. This allows us to calculate viewAdjust below using the
- // unaltered dxViewportTopLeftY value.
- dxViewport.TopLeftY = static_cast<float>(mCurPresentPathFastColorBufferHeight -
- dxViewportTopLeftY - dxViewportHeight);
- }
- else
+ for (UINT i = 0u; i < numRectangles; ++i)
{
- dxViewport.TopLeftY = static_cast<float>(dxViewportTopLeftY);
- }
+ dxViewportTopLeftX = gl::clamp(viewport.x + mViewportOffsets[i].x, dxMinViewportBoundsX,
+ dxMaxViewportBoundsX);
+ dxViewportTopLeftY = gl::clamp(viewport.y + mViewportOffsets[i].y, dxMinViewportBoundsY,
+ dxMaxViewportBoundsY);
+ dxViewportWidth = gl::clamp(viewport.width, 0, dxMaxViewportBoundsX - dxViewportTopLeftX);
+ dxViewportHeight = gl::clamp(viewport.height, 0, dxMaxViewportBoundsY - dxViewportTopLeftY);
+
+ D3D11_VIEWPORT &dxViewport = dxViewports[i];
+ dxViewport.TopLeftX = static_cast<float>(dxViewportTopLeftX);
+ if (mCurPresentPathFastEnabled)
+ {
+ // When present path fast is active and we're rendering to framebuffer 0, we must invert
+ // the viewport in Y-axis.
+ // NOTE: We delay the inversion until right before the call to RSSetViewports, and leave
+ // dxViewportTopLeftY unchanged. This allows us to calculate viewAdjust below using the
+ // unaltered dxViewportTopLeftY value.
+ dxViewport.TopLeftY = static_cast<float>(mCurPresentPathFastColorBufferHeight -
+ dxViewportTopLeftY - dxViewportHeight);
+ }
+ else
+ {
+ dxViewport.TopLeftY = static_cast<float>(dxViewportTopLeftY);
+ }
- dxViewport.Width = static_cast<float>(dxViewportWidth);
- dxViewport.Height = static_cast<float>(dxViewportHeight);
- dxViewport.MinDepth = actualZNear;
- dxViewport.MaxDepth = actualZFar;
+ // The es 3.1 spec section 9.2 states that, "If there are no attachments, rendering
+ // will be limited to a rectangle having a lower left of (0, 0) and an upper right of
+ // (width, height), where width and height are the framebuffer object's default width
+ // and height." See http://anglebug.com/1594
+ // If the Framebuffer has no color attachment and the default width or height is smaller
+ // than the current viewport, use the smaller of the two sizes.
+ // If framebuffer default width or height is 0, the params should not set.
+ if (!framebuffer->getFirstNonNullAttachment() &&
+ (framebuffer->getDefaultWidth() || framebuffer->getDefaultHeight()))
+ {
+ dxViewport.Width =
+ static_cast<GLfloat>(std::min(viewport.width, framebuffer->getDefaultWidth()));
+ dxViewport.Height =
+ static_cast<GLfloat>(std::min(viewport.height, framebuffer->getDefaultHeight()));
+ }
+ else
+ {
+ dxViewport.Width = static_cast<float>(dxViewportWidth);
+ dxViewport.Height = static_cast<float>(dxViewportHeight);
+ }
+ dxViewport.MinDepth = actualZNear;
+ dxViewport.MaxDepth = actualZFar;
+ }
- mRenderer->getDeviceContext()->RSSetViewports(1, &dxViewport);
+ mRenderer->getDeviceContext()->RSSetViewports(numRectangles, dxViewports.data());
mCurViewport = viewport;
mCurNear = actualZNear;
mCurFar = actualZFar;
- // On Feature Level 9_*, we must emulate large and/or negative viewports in the shaders
- // using viewAdjust (like the D3D9 renderer).
+ const D3D11_VIEWPORT adjustViewport = {static_cast<FLOAT>(dxViewportTopLeftX),
+ static_cast<FLOAT>(dxViewportTopLeftY),
+ static_cast<FLOAT>(dxViewportWidth),
+ static_cast<FLOAT>(dxViewportHeight),
+ actualZNear,
+ actualZFar};
+ mShaderConstants.onViewportChange(viewport, adjustViewport, is9_3, mCurPresentPathFastEnabled);
+}
+
+void StateManager11::invalidateRenderTarget()
+{
+ mRenderTargetIsDirty = true;
+}
+
+void StateManager11::processFramebufferInvalidation(const gl::Context *context)
+{
+ if (!mRenderTargetIsDirty)
+ {
+ return;
+ }
+
+ ASSERT(context);
+
+ mRenderTargetIsDirty = false;
+ mInternalDirtyBits.set(DIRTY_BIT_RENDER_TARGET);
+
+ // The pixel shader is dependent on the output layout.
+ invalidateShaders();
+
+ // The D3D11 blend state is heavily dependent on the current render target.
+ mInternalDirtyBits.set(DIRTY_BIT_BLEND_STATE);
+
+ gl::Framebuffer *fbo = context->getGLState().getDrawFramebuffer();
+ ASSERT(fbo);
+
+ // Disable the depth test/depth write if we are using a stencil-only attachment.
+ // This is because ANGLE emulates stencil-only with D24S8 on D3D11 - we should neither read
+ // nor write to the unused depth part of this emulated texture.
+ bool disableDepth = (!fbo->hasDepth() && fbo->hasStencil());
+
+ // Similarly we disable the stencil portion of the DS attachment if the app only binds depth.
+ bool disableStencil = (fbo->hasDepth() && !fbo->hasStencil());
+
+ if (!mCurDisableDepth.valid() || disableDepth != mCurDisableDepth.value() ||
+ !mCurDisableStencil.valid() || disableStencil != mCurDisableStencil.value())
+ {
+ mInternalDirtyBits.set(DIRTY_BIT_DEPTH_STENCIL_STATE);
+ mCurDisableDepth = disableDepth;
+ mCurDisableStencil = disableStencil;
+ }
+
+ bool multiSample = (fbo->getCachedSamples(context) != 0);
+ if (multiSample != mCurRasterState.multiSample)
+ {
+ mInternalDirtyBits.set(DIRTY_BIT_RASTERIZER_STATE);
+ mCurRasterState.multiSample = multiSample;
+ }
+
+ checkPresentPath(context);
+
if (mRenderer->getRenderer11DeviceCaps().featureLevel <= D3D_FEATURE_LEVEL_9_3)
{
- mVertexConstants.viewAdjust[0] = static_cast<float>((viewport.width - dxViewportWidth) +
- 2 * (viewport.x - dxViewportTopLeftX)) /
- dxViewport.Width;
- mVertexConstants.viewAdjust[1] = static_cast<float>((viewport.height - dxViewportHeight) +
- 2 * (viewport.y - dxViewportTopLeftY)) /
- dxViewport.Height;
- mVertexConstants.viewAdjust[2] = static_cast<float>(viewport.width) / dxViewport.Width;
- mVertexConstants.viewAdjust[3] = static_cast<float>(viewport.height) / dxViewport.Height;
+ const auto *firstAttachment = fbo->getFirstNonNullAttachment();
+ if (firstAttachment)
+ {
+ const auto &size = firstAttachment->getSize();
+ if (mViewportBounds.width != size.width || mViewportBounds.height != size.height)
+ {
+ mViewportBounds = gl::Extents(size.width, size.height, 1);
+ invalidateViewport(context);
+ }
+ }
}
+}
- mPixelConstants.viewCoords[0] = viewport.width * 0.5f;
- mPixelConstants.viewCoords[1] = viewport.height * 0.5f;
- mPixelConstants.viewCoords[2] = viewport.x + (viewport.width * 0.5f);
- mPixelConstants.viewCoords[3] = viewport.y + (viewport.height * 0.5f);
+void StateManager11::invalidateBoundViews()
+{
+ mCurVertexSRVs.clear();
+ mCurPixelSRVs.clear();
- // Instanced pointsprite emulation requires ViewCoords to be defined in the
- // the vertex shader.
- mVertexConstants.viewCoords[0] = mPixelConstants.viewCoords[0];
- mVertexConstants.viewCoords[1] = mPixelConstants.viewCoords[1];
- mVertexConstants.viewCoords[2] = mPixelConstants.viewCoords[2];
- mVertexConstants.viewCoords[3] = mPixelConstants.viewCoords[3];
+ invalidateRenderTarget();
+}
- mPixelConstants.depthFront[0] = (actualZFar - actualZNear) * 0.5f;
- mPixelConstants.depthFront[1] = (actualZNear + actualZFar) * 0.5f;
+void StateManager11::invalidateVertexBuffer()
+{
+ unsigned int limit = std::min<unsigned int>(mRenderer->getNativeCaps().maxVertexAttributes,
+ gl::MAX_VERTEX_ATTRIBS);
+ mDirtyVertexBufferRange = gl::RangeUI(0, limit);
+ mInputLayoutIsDirty = true;
+ mInternalDirtyBits.set(DIRTY_BIT_CURRENT_VALUE_ATTRIBS);
+ invalidateVertexAttributeTranslation();
+}
- mVertexConstants.depthRange[0] = actualZNear;
- mVertexConstants.depthRange[1] = actualZFar;
- mVertexConstants.depthRange[2] = actualZFar - actualZNear;
+void StateManager11::invalidateViewport(const gl::Context *context)
+{
+ mInternalDirtyBits.set(DIRTY_BIT_VIEWPORT_STATE);
- mPixelConstants.depthRange[0] = actualZNear;
- mPixelConstants.depthRange[1] = actualZFar;
- mPixelConstants.depthRange[2] = actualZFar - actualZNear;
+ // Viewport affects the driver constants.
+ invalidateDriverUniforms();
+}
- mPixelConstants.viewScale[0] = 1.0f;
- mPixelConstants.viewScale[1] = mCurPresentPathFastEnabled ? 1.0f : -1.0f;
- mPixelConstants.viewScale[2] = 1.0f;
- mPixelConstants.viewScale[3] = 1.0f;
+void StateManager11::invalidateTexturesAndSamplers()
+{
+ mInternalDirtyBits.set(DIRTY_BIT_TEXTURE_AND_SAMPLER_STATE);
+ invalidateSwizzles();
- mVertexConstants.viewScale[0] = mPixelConstants.viewScale[0];
- mVertexConstants.viewScale[1] = mPixelConstants.viewScale[1];
- mVertexConstants.viewScale[2] = mPixelConstants.viewScale[2];
- mVertexConstants.viewScale[3] = mPixelConstants.viewScale[3];
+ // Texture state affects the driver uniforms (base level, etc).
+ invalidateDriverUniforms();
+}
- mViewportStateIsDirty = false;
+void StateManager11::invalidateSwizzles()
+{
+ mDirtySwizzles = true;
}
-void StateManager11::invalidateRenderTarget()
+void StateManager11::invalidateProgramUniforms()
+{
+ mInternalDirtyBits.set(DIRTY_BIT_PROGRAM_UNIFORMS);
+}
+
+void StateManager11::invalidateDriverUniforms()
+{
+ mInternalDirtyBits.set(DIRTY_BIT_DRIVER_UNIFORMS);
+}
+
+void StateManager11::invalidateProgramUniformBuffers()
+{
+ mInternalDirtyBits.set(DIRTY_BIT_PROGRAM_UNIFORM_BUFFERS);
+}
+
+void StateManager11::invalidateConstantBuffer(unsigned int slot)
{
- for (auto &appliedRTV : mAppliedRTVs)
+ if (slot == d3d11::RESERVED_CONSTANT_BUFFER_SLOT_DRIVER)
{
- appliedRTV = angle::DirtyPointer;
+ invalidateDriverUniforms();
+ }
+ else if (slot == d3d11::RESERVED_CONSTANT_BUFFER_SLOT_DEFAULT_UNIFORM_BLOCK)
+ {
+ invalidateProgramUniforms();
+ }
+ else
+ {
+ invalidateProgramUniformBuffers();
}
- mAppliedDSV = angle::DirtyPointer;
}
-void StateManager11::invalidateEverything()
+void StateManager11::invalidateShaders()
{
- mBlendStateIsDirty = true;
- mDepthStencilStateIsDirty = true;
- mRasterizerStateIsDirty = true;
- mScissorStateIsDirty = true;
- mViewportStateIsDirty = true;
+ mInternalDirtyBits.set(DIRTY_BIT_SHADERS);
+}
- // We reset the current SRV data because it might not be in sync with D3D's state
- // anymore. For example when a currently used SRV is used as an RTV, D3D silently
- // remove it from its state.
- mCurVertexSRVs.clear();
- mCurPixelSRVs.clear();
+void StateManager11::setRenderTarget(ID3D11RenderTargetView *rtv, ID3D11DepthStencilView *dsv)
+{
+ if ((rtv && unsetConflictingView(rtv)) || (dsv && unsetConflictingView(dsv)))
+ {
+ mInternalDirtyBits.set(DIRTY_BIT_TEXTURE_AND_SAMPLER_STATE);
+ }
- invalidateRenderTarget();
+ mRenderer->getDeviceContext()->OMSetRenderTargets(1, &rtv, dsv);
+ mInternalDirtyBits.set(DIRTY_BIT_RENDER_TARGET);
}
-bool StateManager11::setRenderTargets(const RenderTargetArray &renderTargets,
- ID3D11DepthStencilView *depthStencil)
+void StateManager11::setRenderTargets(ID3D11RenderTargetView **rtvs,
+ UINT numRTVs,
+ ID3D11DepthStencilView *dsv)
{
- // TODO(jmadill): Use context caps?
- UINT drawBuffers = mRenderer->getRendererCaps().maxDrawBuffers;
+ bool anyDirty = false;
- // Apply the render target and depth stencil
- size_t arraySize = sizeof(uintptr_t) * drawBuffers;
- if (memcmp(renderTargets.data(), mAppliedRTVs.data(), arraySize) == 0 &&
- reinterpret_cast<uintptr_t>(depthStencil) == mAppliedDSV)
+ for (UINT rtvIndex = 0; rtvIndex < numRTVs; ++rtvIndex)
{
- return false;
+ anyDirty = anyDirty || unsetConflictingView(rtvs[rtvIndex]);
}
- // The D3D11 blend state is heavily dependent on the current render target.
- mBlendStateIsDirty = true;
+ if (dsv)
+ {
+ anyDirty = anyDirty || unsetConflictingView(dsv);
+ }
- for (UINT rtIndex = 0; rtIndex < drawBuffers; rtIndex++)
+ if (anyDirty)
{
- mAppliedRTVs[rtIndex] = reinterpret_cast<uintptr_t>(renderTargets[rtIndex]);
+ mInternalDirtyBits.set(DIRTY_BIT_TEXTURE_AND_SAMPLER_STATE);
}
- mAppliedDSV = reinterpret_cast<uintptr_t>(depthStencil);
- mRenderer->getDeviceContext()->OMSetRenderTargets(drawBuffers, renderTargets.data(),
- depthStencil);
- return true;
+ mRenderer->getDeviceContext()->OMSetRenderTargets(numRTVs, (numRTVs > 0) ? rtvs : nullptr, dsv);
+ mInternalDirtyBits.set(DIRTY_BIT_RENDER_TARGET);
}
-void StateManager11::setRenderTarget(ID3D11RenderTargetView *renderTarget,
- ID3D11DepthStencilView *depthStencil)
+void StateManager11::invalidateVertexAttributeTranslation()
{
- mRenderer->getDeviceContext()->OMSetRenderTargets(1, &renderTarget, depthStencil);
+ mVertexAttribsNeedTranslation = true;
}
-void StateManager11::setShaderResource(gl::SamplerType shaderType,
- UINT resourceSlot,
- ID3D11ShaderResourceView *srv)
+void StateManager11::onBeginQuery(Query11 *query)
{
- auto &currentSRVs = (shaderType == gl::SAMPLER_VERTEX ? mCurVertexSRVs : mCurPixelSRVs);
+ mCurrentQueries.insert(query);
+}
- ASSERT(static_cast<size_t>(resourceSlot) < currentSRVs.size());
- const SRVRecord &record = currentSRVs[resourceSlot];
+void StateManager11::onDeleteQueryObject(Query11 *query)
+{
+ mCurrentQueries.erase(query);
+}
- if (record.srv != reinterpret_cast<uintptr_t>(srv))
+gl::Error StateManager11::onMakeCurrent(const gl::Context *context)
+{
+ const gl::State &state = context->getGLState();
+
+ for (Query11 *query : mCurrentQueries)
{
- auto deviceContext = mRenderer->getDeviceContext();
- if (shaderType == gl::SAMPLER_VERTEX)
- {
- deviceContext->VSSetShaderResources(resourceSlot, 1, &srv);
- }
- else
+ ANGLE_TRY(query->pause());
+ }
+ mCurrentQueries.clear();
+
+ for (GLenum queryType : QueryTypes)
+ {
+ gl::Query *query = state.getActiveQuery(queryType);
+ if (query != nullptr)
{
- deviceContext->PSSetShaderResources(resourceSlot, 1, &srv);
+ Query11 *query11 = GetImplAs<Query11>(query);
+ ANGLE_TRY(query11->resume());
+ mCurrentQueries.insert(query11);
}
-
- currentSRVs.update(resourceSlot, srv);
}
+
+ return gl::NoError();
}
gl::Error StateManager11::clearTextures(gl::SamplerType samplerType,
@@ -856,185 +1528,1548 @@ gl::Error StateManager11::clearTextures(gl::SamplerType samplerType,
{
if (rangeStart == rangeEnd)
{
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
auto &currentSRVs = (samplerType == gl::SAMPLER_VERTEX ? mCurVertexSRVs : mCurPixelSRVs);
- gl::Range<size_t> clearRange(rangeStart, rangeStart);
- clearRange.extend(std::min(rangeEnd, currentSRVs.highestUsed()));
-
+ gl::Range<size_t> clearRange(rangeStart, std::min(rangeEnd, currentSRVs.highestUsed()));
if (clearRange.empty())
{
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
- auto deviceContext = mRenderer->getDeviceContext();
+ ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
if (samplerType == gl::SAMPLER_VERTEX)
{
- deviceContext->VSSetShaderResources(static_cast<unsigned int>(rangeStart),
- static_cast<unsigned int>(rangeEnd - rangeStart),
+ deviceContext->VSSetShaderResources(static_cast<unsigned int>(clearRange.low()),
+ static_cast<unsigned int>(clearRange.length()),
&mNullSRVs[0]);
}
else
{
- deviceContext->PSSetShaderResources(static_cast<unsigned int>(rangeStart),
- static_cast<unsigned int>(rangeEnd - rangeStart),
+ deviceContext->PSSetShaderResources(static_cast<unsigned int>(clearRange.low()),
+ static_cast<unsigned int>(clearRange.length()),
&mNullSRVs[0]);
}
- for (size_t samplerIndex = rangeStart; samplerIndex < rangeEnd; ++samplerIndex)
+ for (size_t samplerIndex : clearRange)
{
currentSRVs.update(samplerIndex, nullptr);
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-void StateManager11::unsetConflictingSRVs(gl::SamplerType samplerType,
+bool StateManager11::unsetConflictingView(ID3D11View *view)
+{
+ uintptr_t resource = reinterpret_cast<uintptr_t>(GetViewResource(view));
+ return unsetConflictingSRVs(gl::SAMPLER_VERTEX, resource, nullptr) ||
+ unsetConflictingSRVs(gl::SAMPLER_PIXEL, resource, nullptr);
+}
+
+bool StateManager11::unsetConflictingSRVs(gl::SamplerType samplerType,
uintptr_t resource,
- const gl::ImageIndex &index)
+ const gl::ImageIndex *index)
{
auto &currentSRVs = (samplerType == gl::SAMPLER_VERTEX ? mCurVertexSRVs : mCurPixelSRVs);
+ bool foundOne = false;
+
for (size_t resourceIndex = 0; resourceIndex < currentSRVs.size(); ++resourceIndex)
{
auto &record = currentSRVs[resourceIndex];
if (record.srv && record.resource == resource &&
- ImageIndexConflictsWithSRV(index, record.desc))
+ (!index || ImageIndexConflictsWithSRV(*index, record.desc)))
{
- setShaderResource(samplerType, static_cast<UINT>(resourceIndex), NULL);
+ setShaderResourceInternal<d3d11::ShaderResourceView>(
+ samplerType, static_cast<UINT>(resourceIndex), nullptr);
+ foundOne = true;
}
}
+
+ return foundOne;
+}
+
+void StateManager11::unsetConflictingAttachmentResources(
+ const gl::FramebufferAttachment *attachment,
+ ID3D11Resource *resource)
+{
+ // Unbind render target SRVs from the shader here to prevent D3D11 warnings.
+ if (attachment->type() == GL_TEXTURE)
+ {
+ uintptr_t resourcePtr = reinterpret_cast<uintptr_t>(resource);
+ const gl::ImageIndex &index = attachment->getTextureImageIndex();
+ // The index doesn't need to be corrected for the small compressed texture workaround
+ // because a rendertarget is never compressed.
+ unsetConflictingSRVs(gl::SAMPLER_VERTEX, resourcePtr, &index);
+ unsetConflictingSRVs(gl::SAMPLER_PIXEL, resourcePtr, &index);
+ }
+ else if (attachment->type() == GL_FRAMEBUFFER_DEFAULT)
+ {
+ uintptr_t resourcePtr = reinterpret_cast<uintptr_t>(resource);
+ unsetConflictingSRVs(gl::SAMPLER_VERTEX, resourcePtr, nullptr);
+ unsetConflictingSRVs(gl::SAMPLER_PIXEL, resourcePtr, nullptr);
+ }
}
-void StateManager11::initialize(const gl::Caps &caps)
+gl::Error StateManager11::initialize(const gl::Caps &caps, const gl::Extensions &extensions)
{
mCurVertexSRVs.initialize(caps.maxVertexTextureImageUnits);
mCurPixelSRVs.initialize(caps.maxTextureImageUnits);
// Initialize cached NULL SRV block
mNullSRVs.resize(caps.maxTextureImageUnits, nullptr);
+
+ mCurrentValueAttribs.resize(caps.maxVertexAttributes);
+
+ mForceSetVertexSamplerStates.resize(caps.maxVertexTextureImageUnits, true);
+ mForceSetPixelSamplerStates.resize(caps.maxTextureImageUnits, true);
+ mForceSetComputeSamplerStates.resize(caps.maxComputeTextureImageUnits, true);
+
+ mCurVertexSamplerStates.resize(caps.maxVertexTextureImageUnits);
+ mCurPixelSamplerStates.resize(caps.maxTextureImageUnits);
+ mCurComputeSamplerStates.resize(caps.maxComputeTextureImageUnits);
+
+ mShaderConstants.init(caps);
+
+ mIsMultiviewEnabled = extensions.multiview;
+ mViewportOffsets.resize(1u);
+
+ ANGLE_TRY(mVertexDataManager.initialize());
+
+ mCurrentAttributes.reserve(gl::MAX_VERTEX_ATTRIBS);
+
+ return gl::NoError();
+}
+
+void StateManager11::deinitialize()
+{
+ mCurrentValueAttribs.clear();
+ mInputLayoutCache.clear();
+ mVertexDataManager.deinitialize();
+ mIndexDataManager.deinitialize();
+
+ mDriverConstantBufferVS.reset();
+ mDriverConstantBufferPS.reset();
+ mDriverConstantBufferCS.reset();
}
-gl::Error StateManager11::syncFramebuffer(const gl::Framebuffer *framebuffer)
+gl::Error StateManager11::syncFramebuffer(const gl::Context *context, gl::Framebuffer *framebuffer)
{
- // Get the color render buffer and serial
- // Also extract the render target dimensions and view
- unsigned int renderTargetWidth = 0;
- unsigned int renderTargetHeight = 0;
- DXGI_FORMAT renderTargetFormat = DXGI_FORMAT_UNKNOWN;
- RenderTargetArray framebufferRTVs;
- bool missingColorRenderTarget = true;
+ Framebuffer11 *framebuffer11 = GetImplAs<Framebuffer11>(framebuffer);
+
+ // Applies the render target surface, depth stencil surface, viewport rectangle and
+ // scissor rectangle to the renderer
+ ASSERT(framebuffer && !framebuffer->hasAnyDirtyBit() && framebuffer->cachedComplete());
+
+ // Check for zero-sized default framebuffer, which is a special case.
+ // in this case we do not wish to modify any state and just silently return false.
+ // this will not report any gl error but will cause the calling method to return.
+ if (framebuffer->id() == 0)
+ {
+ ASSERT(!framebuffer11->hasAnyInternalDirtyBit());
+ const gl::Extents &size = framebuffer->getFirstColorbuffer()->getSize();
+ if (size.width == 0 || size.height == 0)
+ {
+ return gl::NoError();
+ }
+ }
+
+ RTVArray framebufferRTVs = {{}};
- framebufferRTVs.fill(nullptr);
+ const auto &colorRTs = framebuffer11->getCachedColorRenderTargets();
- const Framebuffer11 *framebuffer11 = GetImplAs<Framebuffer11>(framebuffer);
- const gl::AttachmentList &colorbuffers = framebuffer11->getColorAttachmentsForRender();
+ size_t appliedRTIndex = 0;
+ bool skipInactiveRTs = mRenderer->getWorkarounds().mrtPerfWorkaround;
+ const auto &drawStates = framebuffer->getDrawBufferStates();
+ gl::DrawBufferMask activeProgramOutputs =
+ context->getContextState().getState().getProgram()->getActiveOutputVariables();
+ UINT maxExistingRT = 0;
- for (size_t colorAttachment = 0; colorAttachment < colorbuffers.size(); ++colorAttachment)
+ for (size_t rtIndex = 0; rtIndex < colorRTs.size(); ++rtIndex)
{
- const gl::FramebufferAttachment *colorbuffer = colorbuffers[colorAttachment];
+ const RenderTarget11 *renderTarget = colorRTs[rtIndex];
- if (colorbuffer)
+ // Skip inactive rendertargets if the workaround is enabled.
+ if (skipInactiveRTs &&
+ (!renderTarget || drawStates[rtIndex] == GL_NONE || !activeProgramOutputs[rtIndex]))
{
- // the draw buffer must be either "none", "back" for the default buffer or the same
- // index as this color (in order)
-
- // check for zero-sized default framebuffer, which is a special case.
- // in this case we do not wish to modify any state and just silently return false.
- // this will not report any gl error but will cause the calling method to return.
- const gl::Extents &size = colorbuffer->getSize();
- if (size.width == 0 || size.height == 0)
- {
- return gl::Error(GL_NO_ERROR);
- }
+ continue;
+ }
- // Extract the render target dimensions and view
- RenderTarget11 *renderTarget = NULL;
- gl::Error error = colorbuffer->getRenderTarget(&renderTarget);
- if (error.isError())
- {
- return error;
- }
- ASSERT(renderTarget);
+ if (renderTarget)
+ {
+ framebufferRTVs[appliedRTIndex] = renderTarget->getRenderTargetView().get();
+ ASSERT(framebufferRTVs[appliedRTIndex]);
+ maxExistingRT = static_cast<UINT>(appliedRTIndex) + 1;
+
+ // Unset conflicting texture SRVs
+ const auto *attachment = framebuffer->getColorbuffer(rtIndex);
+ ASSERT(attachment);
+ unsetConflictingAttachmentResources(attachment, renderTarget->getTexture().get());
+ }
+
+ appliedRTIndex++;
+ }
+
+ // Get the depth stencil buffers
+ ID3D11DepthStencilView *framebufferDSV = nullptr;
+ const auto *depthStencilRenderTarget = framebuffer11->getCachedDepthStencilRenderTarget();
+ if (depthStencilRenderTarget)
+ {
+ framebufferDSV = depthStencilRenderTarget->getDepthStencilView().get();
+ ASSERT(framebufferDSV);
+
+ // Unset conflicting texture SRVs
+ const auto *attachment = framebuffer->getDepthOrStencilbuffer();
+ ASSERT(attachment);
+ unsetConflictingAttachmentResources(attachment,
+ depthStencilRenderTarget->getTexture().get());
+ }
+
+ // TODO(jmadill): Use context caps?
+ ASSERT(maxExistingRT <= static_cast<UINT>(mRenderer->getNativeCaps().maxDrawBuffers));
+
+ // Apply the render target and depth stencil
+ mRenderer->getDeviceContext()->OMSetRenderTargets(maxExistingRT, framebufferRTVs.data(),
+ framebufferDSV);
+
+ return gl::NoError();
+}
+
+void StateManager11::invalidateCurrentValueAttrib(size_t attribIndex)
+{
+ mDirtyCurrentValueAttribs.set(attribIndex);
+ mInternalDirtyBits.set(DIRTY_BIT_CURRENT_VALUE_ATTRIBS);
+}
+
+gl::Error StateManager11::syncCurrentValueAttribs(const gl::State &glState)
+{
+ const auto &activeAttribsMask = glState.getProgram()->getActiveAttribLocationsMask();
+ const auto &dirtyActiveAttribs = (activeAttribsMask & mDirtyCurrentValueAttribs);
+
+ if (!dirtyActiveAttribs.any())
+ {
+ return gl::NoError();
+ }
+
+ const auto &vertexAttributes = glState.getVertexArray()->getVertexAttributes();
+ const auto &vertexBindings = glState.getVertexArray()->getVertexBindings();
+ mDirtyCurrentValueAttribs = (mDirtyCurrentValueAttribs & ~dirtyActiveAttribs);
+
+ for (auto attribIndex : dirtyActiveAttribs)
+ {
+ if (vertexAttributes[attribIndex].enabled)
+ continue;
+
+ const auto *attrib = &vertexAttributes[attribIndex];
+ const auto &currentValue = glState.getVertexAttribCurrentValue(attribIndex);
+ TranslatedAttribute *currentValueAttrib = &mCurrentValueAttribs[attribIndex];
+ currentValueAttrib->currentValueType = currentValue.Type;
+ currentValueAttrib->attribute = attrib;
+ currentValueAttrib->binding = &vertexBindings[attrib->bindingIndex];
+
+ mDirtyVertexBufferRange.extend(static_cast<unsigned int>(attribIndex));
+ mInputLayoutIsDirty = true;
+
+ ANGLE_TRY(mVertexDataManager.storeCurrentValue(currentValue, currentValueAttrib,
+ static_cast<size_t>(attribIndex)));
+ }
+
+ return gl::NoError();
+}
- framebufferRTVs[colorAttachment] = renderTarget->getRenderTargetView();
- ASSERT(framebufferRTVs[colorAttachment]);
+void StateManager11::setInputLayout(const d3d11::InputLayout *inputLayout)
+{
+ ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
+ if (inputLayout == nullptr)
+ {
+ if (!mCurrentInputLayout.empty())
+ {
+ deviceContext->IASetInputLayout(nullptr);
+ mCurrentInputLayout.clear();
+ mInputLayoutIsDirty = true;
+ }
+ }
+ else if (inputLayout->getSerial() != mCurrentInputLayout)
+ {
+ deviceContext->IASetInputLayout(inputLayout->get());
+ mCurrentInputLayout = inputLayout->getSerial();
+ mInputLayoutIsDirty = true;
+ }
+}
+
+bool StateManager11::queueVertexBufferChange(size_t bufferIndex,
+ ID3D11Buffer *buffer,
+ UINT stride,
+ UINT offset)
+{
+ if (buffer != mCurrentVertexBuffers[bufferIndex] ||
+ stride != mCurrentVertexStrides[bufferIndex] ||
+ offset != mCurrentVertexOffsets[bufferIndex])
+ {
+ mInputLayoutIsDirty = true;
+ mDirtyVertexBufferRange.extend(static_cast<unsigned int>(bufferIndex));
+
+ mCurrentVertexBuffers[bufferIndex] = buffer;
+ mCurrentVertexStrides[bufferIndex] = stride;
+ mCurrentVertexOffsets[bufferIndex] = offset;
+ return true;
+ }
+
+ return false;
+}
+
+bool StateManager11::queueVertexOffsetChange(size_t bufferIndex, UINT offsetOnly)
+{
+ if (offsetOnly != mCurrentVertexOffsets[bufferIndex])
+ {
+ mInputLayoutIsDirty = true;
+ mDirtyVertexBufferRange.extend(static_cast<unsigned int>(bufferIndex));
+ mCurrentVertexOffsets[bufferIndex] = offsetOnly;
+ return true;
+ }
+ return false;
+}
- if (missingColorRenderTarget)
+void StateManager11::applyVertexBufferChanges()
+{
+ if (mDirtyVertexBufferRange.empty())
+ {
+ return;
+ }
+
+ ASSERT(mDirtyVertexBufferRange.high() <= gl::MAX_VERTEX_ATTRIBS);
+
+ UINT start = static_cast<UINT>(mDirtyVertexBufferRange.low());
+
+ ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
+ deviceContext->IASetVertexBuffers(start, static_cast<UINT>(mDirtyVertexBufferRange.length()),
+ &mCurrentVertexBuffers[start], &mCurrentVertexStrides[start],
+ &mCurrentVertexOffsets[start]);
+
+ mDirtyVertexBufferRange = gl::RangeUI(gl::MAX_VERTEX_ATTRIBS, 0);
+}
+
+void StateManager11::setSingleVertexBuffer(const d3d11::Buffer *buffer, UINT stride, UINT offset)
+{
+ ID3D11Buffer *native = buffer ? buffer->get() : nullptr;
+ if (queueVertexBufferChange(0, native, stride, offset))
+ {
+ applyVertexBufferChanges();
+ }
+}
+
+gl::Error StateManager11::updateState(const gl::Context *context, GLenum drawMode)
+{
+ const auto &glState = context->getGLState();
+ auto *programD3D = GetImplAs<ProgramD3D>(glState.getProgram());
+
+ // TODO(jmadill): Use dirty bits.
+ processFramebufferInvalidation(context);
+
+ // TODO(jmadill): Use dirty bits.
+ if (programD3D->updateSamplerMapping() == ProgramD3D::SamplerMapping::WasDirty)
+ {
+ invalidateTexturesAndSamplers();
+ }
+
+ // TODO(jmadill): Use dirty bits.
+ if (programD3D->areVertexUniformsDirty() || programD3D->areFragmentUniformsDirty())
+ {
+ mInternalDirtyBits.set(DIRTY_BIT_PROGRAM_UNIFORMS);
+ }
+
+ // Transform feedback affects the stream-out geometry shader.
+ // TODO(jmadill): Use dirty bits.
+ if (glState.isTransformFeedbackActiveUnpaused() != mIsTransformFeedbackCurrentlyActiveUnpaused)
+ {
+ mIsTransformFeedbackCurrentlyActiveUnpaused = glState.isTransformFeedbackActiveUnpaused();
+ invalidateShaders();
+ }
+
+ // Swizzling can cause internal state changes with blit shaders.
+ if (mDirtySwizzles)
+ {
+ ANGLE_TRY(generateSwizzles(context));
+ mDirtySwizzles = false;
+ }
+
+ gl::Framebuffer *framebuffer = glState.getDrawFramebuffer();
+ Framebuffer11 *framebuffer11 = GetImplAs<Framebuffer11>(framebuffer);
+ ANGLE_TRY(framebuffer11->markAttachmentsDirty(context));
+
+ if (framebuffer11->hasAnyInternalDirtyBit())
+ {
+ ASSERT(framebuffer->id() != 0);
+ framebuffer11->syncInternalState(context);
+ }
+
+ bool pointDrawMode = (drawMode == GL_POINTS);
+ if (pointDrawMode != mCurRasterState.pointDrawMode)
+ {
+ mInternalDirtyBits.set(DIRTY_BIT_RASTERIZER_STATE);
+
+ // Changing from points to not points (or vice-versa) affects the geometry shader.
+ invalidateShaders();
+ }
+
+ // TODO(jiawei.shao@intel.com): This can be recomputed only on framebuffer or multisample mask
+ // state changes.
+ RenderTarget11 *firstRT = framebuffer11->getFirstRenderTarget();
+ int samples = (firstRT ? firstRT->getSamples() : 0);
+ unsigned int sampleMask = GetBlendSampleMask(glState, samples);
+ if (sampleMask != mCurSampleMask)
+ {
+ mInternalDirtyBits.set(DIRTY_BIT_BLEND_STATE);
+ }
+
+ // Changing the vertex attribute state can affect the vertex shader.
+ gl::VertexArray *vao = glState.getVertexArray();
+ VertexArray11 *vao11 = GetImplAs<VertexArray11>(vao);
+ if (vao11->flushAttribUpdates(context))
+ {
+ mInternalDirtyBits.set(DIRTY_BIT_SHADERS);
+ }
+
+ auto dirtyBitsCopy = mInternalDirtyBits;
+ mInternalDirtyBits.reset();
+
+ for (auto dirtyBit : dirtyBitsCopy)
+ {
+ switch (dirtyBit)
+ {
+ case DIRTY_BIT_RENDER_TARGET:
+ ANGLE_TRY(syncFramebuffer(context, framebuffer));
+ break;
+ case DIRTY_BIT_VIEWPORT_STATE:
+ syncViewport(context);
+ break;
+ case DIRTY_BIT_SCISSOR_STATE:
+ syncScissorRectangle(glState.getScissor(), glState.isScissorTestEnabled());
+ break;
+ case DIRTY_BIT_RASTERIZER_STATE:
+ ANGLE_TRY(syncRasterizerState(context, pointDrawMode));
+ break;
+ case DIRTY_BIT_BLEND_STATE:
+ ANGLE_TRY(syncBlendState(context, framebuffer, glState.getBlendState(),
+ glState.getBlendColor(), sampleMask));
+ break;
+ case DIRTY_BIT_DEPTH_STENCIL_STATE:
+ ANGLE_TRY(syncDepthStencilState(glState));
+ break;
+ case DIRTY_BIT_TEXTURE_AND_SAMPLER_STATE:
+ // TODO(jmadill): More fine-grained update.
+ ANGLE_TRY(syncTextures(context));
+ break;
+ case DIRTY_BIT_PROGRAM_UNIFORMS:
+ ANGLE_TRY(applyUniforms(programD3D));
+ break;
+ case DIRTY_BIT_DRIVER_UNIFORMS:
+ // This must happen after viewport sync; the viewport affects builtin uniforms.
+ ANGLE_TRY(applyDriverUniforms(*programD3D));
+ break;
+ case DIRTY_BIT_PROGRAM_UNIFORM_BUFFERS:
+ ANGLE_TRY(syncUniformBuffers(context, programD3D));
+ break;
+ case DIRTY_BIT_SHADERS:
+ ANGLE_TRY(syncProgram(context, drawMode));
+ break;
+ case DIRTY_BIT_CURRENT_VALUE_ATTRIBS:
+ ANGLE_TRY(syncCurrentValueAttribs(glState));
+ break;
+ default:
+ UNREACHABLE();
+ break;
+ }
+ }
+
+ ANGLE_TRY(syncTransformFeedbackBuffers(context));
+
+ // Check that we haven't set any dirty bits in the flushing of the dirty bits loop.
+ ASSERT(mInternalDirtyBits.none());
+
+ return gl::NoError();
+}
+
+void StateManager11::setShaderResourceShared(gl::SamplerType shaderType,
+ UINT resourceSlot,
+ const d3d11::SharedSRV *srv)
+{
+ setShaderResourceInternal(shaderType, resourceSlot, srv);
+
+ // TODO(jmadill): Narrower dirty region.
+ mInternalDirtyBits.set(DIRTY_BIT_TEXTURE_AND_SAMPLER_STATE);
+}
+
+void StateManager11::setShaderResource(gl::SamplerType shaderType,
+ UINT resourceSlot,
+ const d3d11::ShaderResourceView *srv)
+{
+ setShaderResourceInternal(shaderType, resourceSlot, srv);
+
+ // TODO(jmadill): Narrower dirty region.
+ mInternalDirtyBits.set(DIRTY_BIT_TEXTURE_AND_SAMPLER_STATE);
+}
+
+void StateManager11::setPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY primitiveTopology)
+{
+ if (primitiveTopology != mCurrentPrimitiveTopology)
+ {
+ mRenderer->getDeviceContext()->IASetPrimitiveTopology(primitiveTopology);
+ mCurrentPrimitiveTopology = primitiveTopology;
+ }
+}
+
+void StateManager11::setDrawShaders(const d3d11::VertexShader *vertexShader,
+ const d3d11::GeometryShader *geometryShader,
+ const d3d11::PixelShader *pixelShader)
+{
+ setVertexShader(vertexShader);
+ setGeometryShader(geometryShader);
+ setPixelShader(pixelShader);
+}
+
+void StateManager11::setVertexShader(const d3d11::VertexShader *shader)
+{
+ ResourceSerial serial = shader ? shader->getSerial() : ResourceSerial(0);
+
+ if (serial != mAppliedVertexShader)
+ {
+ ID3D11VertexShader *appliedShader = shader ? shader->get() : nullptr;
+ mRenderer->getDeviceContext()->VSSetShader(appliedShader, nullptr, 0);
+ mAppliedVertexShader = serial;
+ invalidateShaders();
+ }
+}
+
+void StateManager11::setGeometryShader(const d3d11::GeometryShader *shader)
+{
+ ResourceSerial serial = shader ? shader->getSerial() : ResourceSerial(0);
+
+ if (serial != mAppliedGeometryShader)
+ {
+ ID3D11GeometryShader *appliedShader = shader ? shader->get() : nullptr;
+ mRenderer->getDeviceContext()->GSSetShader(appliedShader, nullptr, 0);
+ mAppliedGeometryShader = serial;
+ invalidateShaders();
+ }
+}
+
+void StateManager11::setPixelShader(const d3d11::PixelShader *shader)
+{
+ ResourceSerial serial = shader ? shader->getSerial() : ResourceSerial(0);
+
+ if (serial != mAppliedPixelShader)
+ {
+ ID3D11PixelShader *appliedShader = shader ? shader->get() : nullptr;
+ mRenderer->getDeviceContext()->PSSetShader(appliedShader, nullptr, 0);
+ mAppliedPixelShader = serial;
+ invalidateShaders();
+ }
+}
+
+void StateManager11::setComputeShader(const d3d11::ComputeShader *shader)
+{
+ ResourceSerial serial = shader ? shader->getSerial() : ResourceSerial(0);
+
+ if (serial != mAppliedComputeShader)
+ {
+ ID3D11ComputeShader *appliedShader = shader ? shader->get() : nullptr;
+ mRenderer->getDeviceContext()->CSSetShader(appliedShader, nullptr, 0);
+ mAppliedComputeShader = serial;
+ // TODO(jmadill): Dirty bits for compute.
+ }
+}
+
+void StateManager11::setVertexConstantBuffer(unsigned int slot, const d3d11::Buffer *buffer)
+{
+ ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
+ auto &currentSerial = mCurrentConstantBufferVS[slot];
+
+ mCurrentConstantBufferVSOffset[slot] = 0;
+ mCurrentConstantBufferVSSize[slot] = 0;
+
+ if (buffer)
+ {
+ if (currentSerial != buffer->getSerial())
+ {
+ deviceContext->VSSetConstantBuffers(slot, 1, buffer->getPointer());
+ currentSerial = buffer->getSerial();
+ invalidateConstantBuffer(slot);
+ }
+ }
+ else
+ {
+ if (!currentSerial.empty())
+ {
+ ID3D11Buffer *nullBuffer = nullptr;
+ deviceContext->VSSetConstantBuffers(slot, 1, &nullBuffer);
+ currentSerial.clear();
+ invalidateConstantBuffer(slot);
+ }
+ }
+}
+
+void StateManager11::setPixelConstantBuffer(unsigned int slot, const d3d11::Buffer *buffer)
+{
+ ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
+ auto &currentSerial = mCurrentConstantBufferPS[slot];
+
+ mCurrentConstantBufferPSOffset[slot] = 0;
+ mCurrentConstantBufferPSSize[slot] = 0;
+
+ if (buffer)
+ {
+ if (currentSerial != buffer->getSerial())
+ {
+ deviceContext->PSSetConstantBuffers(slot, 1, buffer->getPointer());
+ currentSerial = buffer->getSerial();
+ invalidateConstantBuffer(slot);
+ }
+ }
+ else
+ {
+ if (!currentSerial.empty())
+ {
+ ID3D11Buffer *nullBuffer = nullptr;
+ deviceContext->PSSetConstantBuffers(slot, 1, &nullBuffer);
+ currentSerial.clear();
+ invalidateConstantBuffer(slot);
+ }
+ }
+}
+
+void StateManager11::setDepthStencilState(const d3d11::DepthStencilState *depthStencilState,
+ UINT stencilRef)
+{
+ ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
+
+ if (depthStencilState)
+ {
+ deviceContext->OMSetDepthStencilState(depthStencilState->get(), stencilRef);
+ }
+ else
+ {
+ deviceContext->OMSetDepthStencilState(nullptr, stencilRef);
+ }
+
+ mInternalDirtyBits.set(DIRTY_BIT_DEPTH_STENCIL_STATE);
+}
+
+void StateManager11::setSimpleBlendState(const d3d11::BlendState *blendState)
+{
+ ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
+
+ if (blendState)
+ {
+ deviceContext->OMSetBlendState(blendState->get(), nullptr, 0xFFFFFFFF);
+ }
+ else
+ {
+ deviceContext->OMSetBlendState(nullptr, nullptr, 0xFFFFFFFF);
+ }
+
+ mInternalDirtyBits.set(DIRTY_BIT_BLEND_STATE);
+}
+
+void StateManager11::setRasterizerState(const d3d11::RasterizerState *rasterizerState)
+{
+ ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
+
+ if (rasterizerState)
+ {
+ deviceContext->RSSetState(rasterizerState->get());
+ }
+ else
+ {
+ deviceContext->RSSetState(nullptr);
+ }
+
+ mInternalDirtyBits.set(DIRTY_BIT_RASTERIZER_STATE);
+}
+
+void StateManager11::setSimpleViewport(const gl::Extents &extents)
+{
+ setSimpleViewport(extents.width, extents.height);
+}
+
+void StateManager11::setSimpleViewport(int width, int height)
+{
+ D3D11_VIEWPORT viewport;
+ viewport.TopLeftX = 0;
+ viewport.TopLeftY = 0;
+ viewport.Width = static_cast<FLOAT>(width);
+ viewport.Height = static_cast<FLOAT>(height);
+ viewport.MinDepth = 0.0f;
+ viewport.MaxDepth = 1.0f;
+
+ mRenderer->getDeviceContext()->RSSetViewports(1, &viewport);
+ mInternalDirtyBits.set(DIRTY_BIT_VIEWPORT_STATE);
+}
+
+void StateManager11::setSimplePixelTextureAndSampler(const d3d11::SharedSRV &srv,
+ const d3d11::SamplerState &samplerState)
+{
+ ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
+
+ setShaderResourceInternal(gl::SAMPLER_PIXEL, 0, &srv);
+ deviceContext->PSSetSamplers(0, 1, samplerState.getPointer());
+
+ mInternalDirtyBits.set(DIRTY_BIT_TEXTURE_AND_SAMPLER_STATE);
+ mForceSetPixelSamplerStates[0] = true;
+}
+
+void StateManager11::setSimpleScissorRect(const gl::Rectangle &glRect)
+{
+ D3D11_RECT scissorRect;
+ scissorRect.left = glRect.x;
+ scissorRect.right = glRect.x + glRect.width;
+ scissorRect.top = glRect.y;
+ scissorRect.bottom = glRect.y + glRect.height;
+ setScissorRectD3D(scissorRect);
+}
+
+void StateManager11::setScissorRectD3D(const D3D11_RECT &d3dRect)
+{
+ mRenderer->getDeviceContext()->RSSetScissorRects(1, &d3dRect);
+ mInternalDirtyBits.set(DIRTY_BIT_SCISSOR_STATE);
+}
+
+// For each Direct3D sampler of either the pixel or vertex stage,
+// looks up the corresponding OpenGL texture image unit and texture type,
+// and sets the texture and its addressing/filtering state (or NULL when inactive).
+// Sampler mapping needs to be up-to-date on the program object before this is called.
+gl::Error StateManager11::applyTextures(const gl::Context *context, gl::SamplerType shaderType)
+{
+ const auto &glState = context->getGLState();
+ const auto &caps = context->getCaps();
+ ProgramD3D *programD3D = GetImplAs<ProgramD3D>(glState.getProgram());
+
+ ASSERT(!programD3D->isSamplerMappingDirty());
+
+ // TODO(jmadill): Use the Program's sampler bindings.
+ const auto &completeTextures = glState.getCompleteTextureCache();
+
+ unsigned int samplerRange = programD3D->getUsedSamplerRange(shaderType);
+ for (unsigned int samplerIndex = 0; samplerIndex < samplerRange; samplerIndex++)
+ {
+ GLint textureUnit = programD3D->getSamplerMapping(shaderType, samplerIndex, caps);
+ ASSERT(textureUnit != -1);
+ gl::Texture *texture = completeTextures[textureUnit];
+
+ // A nullptr texture indicates incomplete.
+ if (texture)
+ {
+ gl::Sampler *samplerObject = glState.getSampler(textureUnit);
+
+ const gl::SamplerState &samplerState =
+ samplerObject ? samplerObject->getSamplerState() : texture->getSamplerState();
+
+ ANGLE_TRY(setSamplerState(context, shaderType, samplerIndex, texture, samplerState));
+ ANGLE_TRY(setTexture(context, shaderType, samplerIndex, texture));
+ }
+ else
+ {
+ GLenum textureType = programD3D->getSamplerTextureType(shaderType, samplerIndex);
+
+ // Texture is not sampler complete or it is in use by the framebuffer. Bind the
+ // incomplete texture.
+ gl::Texture *incompleteTexture = nullptr;
+ ANGLE_TRY(mRenderer->getIncompleteTexture(context, textureType, &incompleteTexture));
+ ANGLE_TRY(setSamplerState(context, shaderType, samplerIndex, incompleteTexture,
+ incompleteTexture->getSamplerState()));
+ ANGLE_TRY(setTexture(context, shaderType, samplerIndex, incompleteTexture));
+ }
+ }
+
+ // Set all the remaining textures to NULL
+ size_t samplerCount = (shaderType == gl::SAMPLER_PIXEL) ? caps.maxTextureImageUnits
+ : caps.maxVertexTextureImageUnits;
+ ANGLE_TRY(clearTextures(shaderType, samplerRange, samplerCount));
+
+ return gl::NoError();
+}
+
+gl::Error StateManager11::syncTextures(const gl::Context *context)
+{
+ ANGLE_TRY(applyTextures(context, gl::SAMPLER_VERTEX));
+ ANGLE_TRY(applyTextures(context, gl::SAMPLER_PIXEL));
+ return gl::NoError();
+}
+
+gl::Error StateManager11::setSamplerState(const gl::Context *context,
+ gl::SamplerType type,
+ int index,
+ gl::Texture *texture,
+ const gl::SamplerState &samplerState)
+{
+#if !defined(NDEBUG)
+ // Storage should exist, texture should be complete. Only verified in Debug.
+ TextureD3D *textureD3D = GetImplAs<TextureD3D>(texture);
+ TextureStorage *storage = nullptr;
+ ANGLE_TRY(textureD3D->getNativeTexture(context, &storage));
+ ASSERT(storage);
+#endif // !defined(NDEBUG)
+
+ auto *deviceContext = mRenderer->getDeviceContext();
+
+ if (type == gl::SAMPLER_PIXEL)
+ {
+ ASSERT(static_cast<unsigned int>(index) < mRenderer->getNativeCaps().maxTextureImageUnits);
+
+ if (mForceSetPixelSamplerStates[index] ||
+ memcmp(&samplerState, &mCurPixelSamplerStates[index], sizeof(gl::SamplerState)) != 0)
+ {
+ ID3D11SamplerState *dxSamplerState = nullptr;
+ ANGLE_TRY(mRenderer->getSamplerState(samplerState, &dxSamplerState));
+
+ ASSERT(dxSamplerState != nullptr);
+ deviceContext->PSSetSamplers(index, 1, &dxSamplerState);
+
+ mCurPixelSamplerStates[index] = samplerState;
+ }
+
+ mForceSetPixelSamplerStates[index] = false;
+ }
+ else if (type == gl::SAMPLER_VERTEX)
+ {
+ ASSERT(static_cast<unsigned int>(index) <
+ mRenderer->getNativeCaps().maxVertexTextureImageUnits);
+
+ if (mForceSetVertexSamplerStates[index] ||
+ memcmp(&samplerState, &mCurVertexSamplerStates[index], sizeof(gl::SamplerState)) != 0)
+ {
+ ID3D11SamplerState *dxSamplerState = nullptr;
+ ANGLE_TRY(mRenderer->getSamplerState(samplerState, &dxSamplerState));
+
+ ASSERT(dxSamplerState != nullptr);
+ deviceContext->VSSetSamplers(index, 1, &dxSamplerState);
+
+ mCurVertexSamplerStates[index] = samplerState;
+ }
+
+ mForceSetVertexSamplerStates[index] = false;
+ }
+ else if (type == gl::SAMPLER_COMPUTE)
+ {
+ ASSERT(static_cast<unsigned int>(index) <
+ mRenderer->getNativeCaps().maxComputeTextureImageUnits);
+
+ if (mForceSetComputeSamplerStates[index] ||
+ memcmp(&samplerState, &mCurComputeSamplerStates[index], sizeof(gl::SamplerState)) != 0)
+ {
+ ID3D11SamplerState *dxSamplerState = nullptr;
+ ANGLE_TRY(mRenderer->getSamplerState(samplerState, &dxSamplerState));
+
+ ASSERT(dxSamplerState != nullptr);
+ deviceContext->CSSetSamplers(index, 1, &dxSamplerState);
+
+ mCurComputeSamplerStates[index] = samplerState;
+ }
+
+ mForceSetComputeSamplerStates[index] = false;
+ }
+ else
+ UNREACHABLE();
+
+ // Sampler metadata that's passed to shaders in uniforms is stored separately from rest of the
+ // sampler state since having it in contiguous memory makes it possible to memcpy to a constant
+ // buffer, and it doesn't affect the state set by PSSetSamplers/VSSetSamplers.
+ mShaderConstants.onSamplerChange(type, index, *texture);
+
+ return gl::NoError();
+}
+
+gl::Error StateManager11::setTexture(const gl::Context *context,
+ gl::SamplerType type,
+ int index,
+ gl::Texture *texture)
+{
+ const d3d11::SharedSRV *textureSRV = nullptr;
+
+ if (texture)
+ {
+ TextureD3D *textureImpl = GetImplAs<TextureD3D>(texture);
+
+ TextureStorage *texStorage = nullptr;
+ ANGLE_TRY(textureImpl->getNativeTexture(context, &texStorage));
+
+ // Texture should be complete and have a storage
+ ASSERT(texStorage);
+
+ TextureStorage11 *storage11 = GetAs<TextureStorage11>(texStorage);
+
+ ANGLE_TRY(storage11->getSRV(context, texture->getTextureState(), &textureSRV));
+
+ // If we get an invalid SRV here, something went wrong in the texture class and we're
+ // unexpectedly missing the shader resource view.
+ ASSERT(textureSRV->valid());
+
+ textureImpl->resetDirty();
+ }
+
+ ASSERT(
+ (type == gl::SAMPLER_PIXEL &&
+ static_cast<unsigned int>(index) < mRenderer->getNativeCaps().maxTextureImageUnits) ||
+ (type == gl::SAMPLER_VERTEX &&
+ static_cast<unsigned int>(index) < mRenderer->getNativeCaps().maxVertexTextureImageUnits));
+
+ setShaderResourceInternal(type, index, textureSRV);
+ return gl::NoError();
+}
+
+// Things that affect a program's dirtyness:
+// 1. Directly changing the program executable -> triggered in StateManager11::syncState.
+// 2. The vertex attribute layout -> triggered in VertexArray11::syncState/signal.
+// 3. The fragment shader's rendertargets -> triggered in Framebuffer11::syncState/signal.
+// 4. Enabling/disabling rasterizer discard. -> triggered in StateManager11::syncState.
+// 5. Enabling/disabling transform feedback. -> checked in StateManager11::updateState.
+// 6. An internal shader was used. -> triggered in StateManager11::set*Shader.
+// 7. Drawing with/without point sprites. -> checked in StateManager11::updateState.
+// TODO(jmadill): Use dirty bits for transform feedback.
+gl::Error StateManager11::syncProgram(const gl::Context *context, GLenum drawMode)
+{
+ Context11 *context11 = GetImplAs<Context11>(context);
+ ANGLE_TRY(context11->triggerDrawCallProgramRecompilation(context, drawMode));
+
+ const auto &glState = context->getGLState();
+ const auto *va11 = GetImplAs<VertexArray11>(glState.getVertexArray());
+ auto *programD3D = GetImplAs<ProgramD3D>(glState.getProgram());
+
+ programD3D->updateCachedInputLayout(va11->getCurrentStateSerial(), glState);
+
+ // Binaries must be compiled before the sync.
+ ASSERT(programD3D->hasVertexExecutableForCachedInputLayout());
+ ASSERT(programD3D->hasGeometryExecutableForPrimitiveType(drawMode));
+ ASSERT(programD3D->hasPixelExecutableForCachedOutputLayout());
+
+ ShaderExecutableD3D *vertexExe = nullptr;
+ ANGLE_TRY(programD3D->getVertexExecutableForCachedInputLayout(&vertexExe, nullptr));
+
+ ShaderExecutableD3D *pixelExe = nullptr;
+ ANGLE_TRY(programD3D->getPixelExecutableForCachedOutputLayout(&pixelExe, nullptr));
+
+ ShaderExecutableD3D *geometryExe = nullptr;
+ ANGLE_TRY(programD3D->getGeometryExecutableForPrimitiveType(context, drawMode, &geometryExe,
+ nullptr));
+
+ const d3d11::VertexShader *vertexShader =
+ (vertexExe ? &GetAs<ShaderExecutable11>(vertexExe)->getVertexShader() : nullptr);
+
+ // Skip pixel shader if we're doing rasterizer discard.
+ const d3d11::PixelShader *pixelShader = nullptr;
+ if (!glState.getRasterizerState().rasterizerDiscard)
+ {
+ pixelShader = (pixelExe ? &GetAs<ShaderExecutable11>(pixelExe)->getPixelShader() : nullptr);
+ }
+
+ const d3d11::GeometryShader *geometryShader = nullptr;
+ if (glState.isTransformFeedbackActiveUnpaused())
+ {
+ geometryShader =
+ (vertexExe ? &GetAs<ShaderExecutable11>(vertexExe)->getStreamOutShader() : nullptr);
+ }
+ else
+ {
+ geometryShader =
+ (geometryExe ? &GetAs<ShaderExecutable11>(geometryExe)->getGeometryShader() : nullptr);
+ }
+
+ setDrawShaders(vertexShader, geometryShader, pixelShader);
+
+ // Explicitly clear the shaders dirty bit.
+ mInternalDirtyBits.reset(DIRTY_BIT_SHADERS);
+
+ return gl::NoError();
+}
+
+gl::Error StateManager11::applyVertexBuffer(const gl::Context *context,
+ GLenum mode,
+ const DrawCallVertexParams &vertexParams,
+ bool isIndexedRendering)
+{
+ const auto &state = context->getGLState();
+ const gl::VertexArray *vertexArray = state.getVertexArray();
+ VertexArray11 *vertexArray11 = GetImplAs<VertexArray11>(vertexArray);
+
+ if (mVertexAttribsNeedTranslation)
+ {
+ ANGLE_TRY(vertexArray11->updateDirtyAndDynamicAttribs(context, &mVertexDataManager,
+ vertexParams));
+ mInputLayoutIsDirty = true;
+
+ // Determine if we need to update attribs on the next draw.
+ mVertexAttribsNeedTranslation = (vertexArray11->hasActiveDynamicAttrib(context));
+ }
+
+ if (!mLastFirstVertex.valid() || mLastFirstVertex.value() != vertexParams.firstVertex())
+ {
+ mLastFirstVertex = vertexParams.firstVertex();
+ mInputLayoutIsDirty = true;
+ }
+
+ if (!mInputLayoutIsDirty)
+ {
+ return gl::NoError();
+ }
+
+ const auto &vertexArrayAttribs = vertexArray11->getTranslatedAttribs();
+ gl::Program *program = state.getProgram();
+
+ // Sort the attributes according to ensure we re-use similar input layouts.
+ AttribIndexArray sortedSemanticIndices;
+ SortAttributesByLayout(program, vertexArrayAttribs, mCurrentValueAttribs,
+ &sortedSemanticIndices, &mCurrentAttributes);
+
+ auto featureLevel = mRenderer->getRenderer11DeviceCaps().featureLevel;
+
+ // If we are using FL 9_3, make sure the first attribute is not instanced
+ if (featureLevel <= D3D_FEATURE_LEVEL_9_3 && !mCurrentAttributes.empty())
+ {
+ if (mCurrentAttributes[0]->divisor > 0)
+ {
+ Optional<size_t> firstNonInstancedIndex = FindFirstNonInstanced(mCurrentAttributes);
+ if (firstNonInstancedIndex.valid())
{
- renderTargetWidth = renderTarget->getWidth();
- renderTargetHeight = renderTarget->getHeight();
- renderTargetFormat = renderTarget->getDXGIFormat();
- missingColorRenderTarget = false;
+ size_t index = firstNonInstancedIndex.value();
+ std::swap(mCurrentAttributes[0], mCurrentAttributes[index]);
+ std::swap(sortedSemanticIndices[0], sortedSemanticIndices[index]);
}
+ }
+ }
+
+ // Update the applied input layout by querying the cache.
+ ANGLE_TRY(mInputLayoutCache.updateInputLayout(mRenderer, state, mCurrentAttributes, mode,
+ sortedSemanticIndices, vertexParams));
+
+ // Update the applied vertex buffers.
+ ANGLE_TRY(mInputLayoutCache.applyVertexBuffers(context, mCurrentAttributes, mode,
+ vertexParams.firstVertex(), isIndexedRendering));
+
+ // InputLayoutCache::applyVertexBuffers calls through to the Bufer11 to get the native vertex
+ // buffer (ID3D11Buffer *). Because we allocate these buffers lazily, this will trigger
+ // allocation. This in turn will signal that the buffer is dirty. Since we just resolved the
+ // dirty-ness in VertexArray11::updateDirtyAndDynamicAttribs, this can make us do a needless
+ // update on the second draw call.
+ // Hence we clear the flags here, after we've applied vertex data, since we know everything
+ // is clean. This is a bit of a hack.
+ vertexArray11->clearDirtyAndPromoteDynamicAttribs(context, vertexParams);
+
+ mInputLayoutIsDirty = false;
+ return gl::NoError();
+}
+
+gl::Error StateManager11::applyIndexBuffer(const gl::Context *context,
+ const void *indices,
+ GLsizei count,
+ GLenum type,
+ const gl::HasIndexRange &lazyIndexRange,
+ bool usePrimitiveRestartWorkaround)
+{
+ const auto &glState = context->getGLState();
+ gl::VertexArray *vao = glState.getVertexArray();
+ VertexArray11 *vao11 = GetImplAs<VertexArray11>(vao);
+
+ GLenum destElementType =
+ GetIndexTranslationDestType(type, lazyIndexRange, usePrimitiveRestartWorkaround);
+
+ if (!vao11->updateElementArrayStorage(context, type, destElementType, indices) &&
+ !mIndexBufferIsDirty)
+ {
+ // No streaming or index buffer application necessary.
+ return gl::NoError();
+ }
+
+ gl::Buffer *elementArrayBuffer = vao->getElementArrayBuffer().get();
+
+ TranslatedIndexData *indexInfo = vao11->getCachedIndexInfo();
+ ANGLE_TRY(mIndexDataManager.prepareIndexData(context, type, destElementType, count,
+ elementArrayBuffer, indices, indexInfo));
+
+ ID3D11Buffer *buffer = nullptr;
+ DXGI_FORMAT bufferFormat =
+ (indexInfo->indexType == GL_UNSIGNED_INT) ? DXGI_FORMAT_R32_UINT : DXGI_FORMAT_R16_UINT;
+
+ if (indexInfo->storage)
+ {
+ Buffer11 *storage = GetAs<Buffer11>(indexInfo->storage);
+ ANGLE_TRY_RESULT(storage->getBuffer(context, BUFFER_USAGE_INDEX), buffer);
+ }
+ else
+ {
+ IndexBuffer11 *indexBuffer = GetAs<IndexBuffer11>(indexInfo->indexBuffer);
+ buffer = indexBuffer->getBuffer().get();
+ }
+
+ // Track dirty indices in the index range cache.
+ indexInfo->srcIndexData.srcIndicesChanged =
+ syncIndexBuffer(buffer, bufferFormat, indexInfo->startOffset);
+
+ mIndexBufferIsDirty = false;
+
+ vao11->setCachedIndexInfoValid();
+ return gl::NoError();
+}
+
+void StateManager11::setIndexBuffer(ID3D11Buffer *buffer,
+ DXGI_FORMAT indexFormat,
+ unsigned int offset)
+{
+ if (syncIndexBuffer(buffer, indexFormat, offset))
+ {
+ mIndexBufferIsDirty = true;
+ }
+}
- // Unbind render target SRVs from the shader here to prevent D3D11 warnings.
- if (colorbuffer->type() == GL_TEXTURE)
+bool StateManager11::syncIndexBuffer(ID3D11Buffer *buffer,
+ DXGI_FORMAT indexFormat,
+ unsigned int offset)
+{
+ if (buffer != mAppliedIB || indexFormat != mAppliedIBFormat || offset != mAppliedIBOffset)
+ {
+ mRenderer->getDeviceContext()->IASetIndexBuffer(buffer, indexFormat, offset);
+
+ mAppliedIB = buffer;
+ mAppliedIBFormat = indexFormat;
+ mAppliedIBOffset = offset;
+ return true;
+ }
+
+ return false;
+}
+
+// Vertex buffer is invalidated outside this function.
+gl::Error StateManager11::updateVertexOffsetsForPointSpritesEmulation(GLint startVertex,
+ GLsizei emulatedInstanceId)
+{
+ return mInputLayoutCache.updateVertexOffsetsForPointSpritesEmulation(
+ mRenderer, mCurrentAttributes, startVertex, emulatedInstanceId);
+}
+
+gl::Error StateManager11::generateSwizzle(const gl::Context *context, gl::Texture *texture)
+{
+ if (!texture)
+ {
+ return gl::NoError();
+ }
+
+ TextureD3D *textureD3D = GetImplAs<TextureD3D>(texture);
+ ASSERT(textureD3D);
+
+ TextureStorage *texStorage = nullptr;
+ ANGLE_TRY(textureD3D->getNativeTexture(context, &texStorage));
+
+ if (texStorage)
+ {
+ TextureStorage11 *storage11 = GetAs<TextureStorage11>(texStorage);
+ const gl::TextureState &textureState = texture->getTextureState();
+ ANGLE_TRY(storage11->generateSwizzles(context, textureState.getSwizzleState()));
+ }
+
+ return gl::NoError();
+}
+
+gl::Error StateManager11::generateSwizzlesForShader(const gl::Context *context,
+ gl::SamplerType type)
+{
+ const auto &glState = context->getGLState();
+ ProgramD3D *programD3D = GetImplAs<ProgramD3D>(glState.getProgram());
+
+ unsigned int samplerRange = programD3D->getUsedSamplerRange(type);
+
+ for (unsigned int i = 0; i < samplerRange; i++)
+ {
+ GLenum textureType = programD3D->getSamplerTextureType(type, i);
+ GLint textureUnit = programD3D->getSamplerMapping(type, i, context->getCaps());
+ if (textureUnit != -1)
+ {
+ gl::Texture *texture = glState.getSamplerTexture(textureUnit, textureType);
+ ASSERT(texture);
+ if (texture->getTextureState().swizzleRequired())
{
- uintptr_t rtResource =
- reinterpret_cast<uintptr_t>(GetViewResource(framebufferRTVs[colorAttachment]));
- const gl::ImageIndex &index = colorbuffer->getTextureImageIndex();
- // The index doesn't need to be corrected for the small compressed texture
- // workaround
- // because a rendertarget is never compressed.
- unsetConflictingSRVs(gl::SAMPLER_VERTEX, rtResource, index);
- unsetConflictingSRVs(gl::SAMPLER_PIXEL, rtResource, index);
+ ANGLE_TRY(generateSwizzle(context, texture));
}
}
}
- // Get the depth stencil buffers
- ID3D11DepthStencilView *framebufferDSV = NULL;
- const gl::FramebufferAttachment *depthStencil = framebuffer->getDepthOrStencilbuffer();
- if (depthStencil)
+ return gl::NoError();
+}
+
+gl::Error StateManager11::generateSwizzles(const gl::Context *context)
+{
+ ANGLE_TRY(generateSwizzlesForShader(context, gl::SAMPLER_VERTEX));
+ ANGLE_TRY(generateSwizzlesForShader(context, gl::SAMPLER_PIXEL));
+ return gl::NoError();
+}
+
+gl::Error StateManager11::applyUniforms(ProgramD3D *programD3D)
+{
+ UniformStorage11 *vertexUniformStorage =
+ GetAs<UniformStorage11>(&programD3D->getVertexUniformStorage());
+ UniformStorage11 *fragmentUniformStorage =
+ GetAs<UniformStorage11>(&programD3D->getFragmentUniformStorage());
+ ASSERT(vertexUniformStorage);
+ ASSERT(fragmentUniformStorage);
+
+ ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
+
+ const d3d11::Buffer *vertexConstantBuffer = nullptr;
+ ANGLE_TRY(vertexUniformStorage->getConstantBuffer(mRenderer, &vertexConstantBuffer));
+ const d3d11::Buffer *pixelConstantBuffer = nullptr;
+ ANGLE_TRY(fragmentUniformStorage->getConstantBuffer(mRenderer, &pixelConstantBuffer));
+
+ if (vertexUniformStorage->size() > 0 && programD3D->areVertexUniformsDirty())
+ {
+ UpdateUniformBuffer(deviceContext, vertexUniformStorage, vertexConstantBuffer);
+ }
+
+ if (fragmentUniformStorage->size() > 0 && programD3D->areFragmentUniformsDirty())
+ {
+ UpdateUniformBuffer(deviceContext, fragmentUniformStorage, pixelConstantBuffer);
+ }
+
+ unsigned int slot = d3d11::RESERVED_CONSTANT_BUFFER_SLOT_DEFAULT_UNIFORM_BLOCK;
+
+ if (mCurrentConstantBufferVS[slot] != vertexConstantBuffer->getSerial())
+ {
+ deviceContext->VSSetConstantBuffers(slot, 1, vertexConstantBuffer->getPointer());
+ mCurrentConstantBufferVS[slot] = vertexConstantBuffer->getSerial();
+ mCurrentConstantBufferVSOffset[slot] = 0;
+ mCurrentConstantBufferVSSize[slot] = 0;
+ }
+
+ if (mCurrentConstantBufferPS[slot] != pixelConstantBuffer->getSerial())
+ {
+ deviceContext->PSSetConstantBuffers(slot, 1, pixelConstantBuffer->getPointer());
+ mCurrentConstantBufferPS[slot] = pixelConstantBuffer->getSerial();
+ mCurrentConstantBufferPSOffset[slot] = 0;
+ mCurrentConstantBufferPSSize[slot] = 0;
+ }
+
+ programD3D->markUniformsClean();
+
+ return gl::NoError();
+}
+
+gl::Error StateManager11::applyDriverUniforms(const ProgramD3D &programD3D)
+{
+ ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
+
+ if (!mDriverConstantBufferVS.valid())
+ {
+ size_t requiredSize = mShaderConstants.getRequiredBufferSize(gl::SAMPLER_VERTEX);
+
+ D3D11_BUFFER_DESC constantBufferDescription = {0};
+ d3d11::InitConstantBufferDesc(&constantBufferDescription, requiredSize);
+ ANGLE_TRY(mRenderer->allocateResource(constantBufferDescription, &mDriverConstantBufferVS));
+
+ ID3D11Buffer *driverVSConstants = mDriverConstantBufferVS.get();
+ deviceContext->VSSetConstantBuffers(d3d11::RESERVED_CONSTANT_BUFFER_SLOT_DRIVER, 1,
+ &driverVSConstants);
+ }
+
+ if (!mDriverConstantBufferPS.valid())
+ {
+ size_t requiredSize = mShaderConstants.getRequiredBufferSize(gl::SAMPLER_PIXEL);
+
+ D3D11_BUFFER_DESC constantBufferDescription = {0};
+ d3d11::InitConstantBufferDesc(&constantBufferDescription, requiredSize);
+ ANGLE_TRY(mRenderer->allocateResource(constantBufferDescription, &mDriverConstantBufferPS));
+
+ ID3D11Buffer *driverVSConstants = mDriverConstantBufferPS.get();
+ deviceContext->PSSetConstantBuffers(d3d11::RESERVED_CONSTANT_BUFFER_SLOT_DRIVER, 1,
+ &driverVSConstants);
+ }
+
+ // Sampler metadata and driver constants need to coexist in the same constant buffer to conserve
+ // constant buffer slots. We update both in the constant buffer if needed.
+ ANGLE_TRY(mShaderConstants.updateBuffer(deviceContext, gl::SAMPLER_VERTEX, programD3D,
+ mDriverConstantBufferVS));
+ ANGLE_TRY(mShaderConstants.updateBuffer(deviceContext, gl::SAMPLER_PIXEL, programD3D,
+ mDriverConstantBufferPS));
+
+ // needed for the point sprite geometry shader
+ // GSSetConstantBuffers triggers device removal on 9_3, so we should only call it for ES3.
+ if (mRenderer->isES3Capable())
{
- RenderTarget11 *depthStencilRenderTarget = NULL;
- gl::Error error = depthStencil->getRenderTarget(&depthStencilRenderTarget);
- if (error.isError())
+ if (mCurrentGeometryConstantBuffer != mDriverConstantBufferPS.getSerial())
{
- return error;
+ ASSERT(mDriverConstantBufferPS.valid());
+ deviceContext->GSSetConstantBuffers(0, 1, mDriverConstantBufferPS.getPointer());
+ mCurrentGeometryConstantBuffer = mDriverConstantBufferPS.getSerial();
}
- ASSERT(depthStencilRenderTarget);
+ }
- framebufferDSV = depthStencilRenderTarget->getDepthStencilView();
- ASSERT(framebufferDSV);
+ return gl::NoError();
+}
+
+gl::Error StateManager11::applyComputeUniforms(ProgramD3D *programD3D)
+{
+ UniformStorage11 *computeUniformStorage =
+ GetAs<UniformStorage11>(&programD3D->getComputeUniformStorage());
+ ASSERT(computeUniformStorage);
+
+ const d3d11::Buffer *constantBuffer = nullptr;
+ ANGLE_TRY(computeUniformStorage->getConstantBuffer(mRenderer, &constantBuffer));
+
+ ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
+
+ if (computeUniformStorage->size() > 0 && programD3D->areComputeUniformsDirty())
+ {
+ UpdateUniformBuffer(deviceContext, computeUniformStorage, constantBuffer);
+ programD3D->markUniformsClean();
+ }
+
+ if (mCurrentComputeConstantBuffer != constantBuffer->getSerial())
+ {
+ deviceContext->CSSetConstantBuffers(
+ d3d11::RESERVED_CONSTANT_BUFFER_SLOT_DEFAULT_UNIFORM_BLOCK, 1,
+ constantBuffer->getPointer());
+ mCurrentComputeConstantBuffer = constantBuffer->getSerial();
+ }
+
+ if (!mDriverConstantBufferCS.valid())
+ {
+ size_t requiredSize = mShaderConstants.getRequiredBufferSize(gl::SAMPLER_COMPUTE);
+
+ D3D11_BUFFER_DESC constantBufferDescription = {0};
+ d3d11::InitConstantBufferDesc(&constantBufferDescription, requiredSize);
+ ANGLE_TRY(mRenderer->allocateResource(constantBufferDescription, &mDriverConstantBufferCS));
+ ID3D11Buffer *buffer = mDriverConstantBufferCS.get();
+ deviceContext->CSSetConstantBuffers(d3d11::RESERVED_CONSTANT_BUFFER_SLOT_DRIVER, 1,
+ &buffer);
+ }
+
+ ANGLE_TRY(mShaderConstants.updateBuffer(deviceContext, gl::SAMPLER_COMPUTE, *programD3D,
+ mDriverConstantBufferCS));
+
+ return gl::NoError();
+}
+
+gl::Error StateManager11::syncUniformBuffers(const gl::Context *context, ProgramD3D *programD3D)
+{
+ unsigned int reservedVertex = mRenderer->getReservedVertexUniformBuffers();
+ unsigned int reservedFragment = mRenderer->getReservedFragmentUniformBuffers();
+
+ programD3D->updateUniformBufferCache(context->getCaps(), reservedVertex, reservedFragment);
+
+ const auto &vertexUniformBuffers = programD3D->getVertexUniformBufferCache();
+ const auto &fragmentUniformBuffers = programD3D->getFragmentUniformBufferCache();
+ const auto &glState = context->getGLState();
+ ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
+ ID3D11DeviceContext1 *deviceContext1 = mRenderer->getDeviceContext1IfSupported();
+
+ for (size_t bufferIndex = 0; bufferIndex < vertexUniformBuffers.size(); bufferIndex++)
+ {
+ GLint binding = vertexUniformBuffers[bufferIndex];
+
+ if (binding == -1)
+ {
+ continue;
+ }
+
+ const auto &uniformBuffer = glState.getIndexedUniformBuffer(binding);
+ GLintptr uniformBufferOffset = uniformBuffer.getOffset();
+ GLsizeiptr uniformBufferSize = uniformBuffer.getSize();
+
+ if (uniformBuffer.get() == nullptr)
+ {
+ continue;
+ }
+
+ Buffer11 *bufferStorage = GetImplAs<Buffer11>(uniformBuffer.get());
+ const d3d11::Buffer *constantBuffer = nullptr;
+ UINT firstConstant = 0;
+ UINT numConstants = 0;
+
+ ANGLE_TRY(bufferStorage->getConstantBufferRange(context, uniformBufferOffset,
+ uniformBufferSize, &constantBuffer,
+ &firstConstant, &numConstants));
+
+ ASSERT(constantBuffer);
+
+ if (mCurrentConstantBufferVS[bufferIndex] == constantBuffer->getSerial() &&
+ mCurrentConstantBufferVSOffset[bufferIndex] == uniformBufferOffset &&
+ mCurrentConstantBufferVSSize[bufferIndex] == uniformBufferSize)
+ {
+ continue;
+ }
+
+ unsigned int appliedIndex = reservedVertex + static_cast<unsigned int>(bufferIndex);
+
+ if (firstConstant != 0 && uniformBufferSize != 0)
+ {
+ ASSERT(numConstants != 0);
+ deviceContext1->VSSetConstantBuffers1(appliedIndex, 1, constantBuffer->getPointer(),
+ &firstConstant, &numConstants);
+ }
+ else
+ {
+ deviceContext->VSSetConstantBuffers(appliedIndex, 1, constantBuffer->getPointer());
+ }
+
+ mCurrentConstantBufferVS[appliedIndex] = constantBuffer->getSerial();
+ mCurrentConstantBufferVSOffset[appliedIndex] = uniformBufferOffset;
+ mCurrentConstantBufferVSSize[appliedIndex] = uniformBufferSize;
+ }
+
+ for (size_t bufferIndex = 0; bufferIndex < fragmentUniformBuffers.size(); bufferIndex++)
+ {
+ GLint binding = fragmentUniformBuffers[bufferIndex];
- // If there is no render buffer, the width, height and format values come from
- // the depth stencil
- if (missingColorRenderTarget)
+ if (binding == -1)
{
- renderTargetWidth = depthStencilRenderTarget->getWidth();
- renderTargetHeight = depthStencilRenderTarget->getHeight();
+ continue;
}
- // Unbind render target SRVs from the shader here to prevent D3D11 warnings.
- if (depthStencil->type() == GL_TEXTURE)
+ const auto &uniformBuffer = glState.getIndexedUniformBuffer(binding);
+ GLintptr uniformBufferOffset = uniformBuffer.getOffset();
+ GLsizeiptr uniformBufferSize = uniformBuffer.getSize();
+
+ if (uniformBuffer.get() == nullptr)
{
- uintptr_t depthStencilResource =
- reinterpret_cast<uintptr_t>(GetViewResource(framebufferDSV));
- const gl::ImageIndex &index = depthStencil->getTextureImageIndex();
- // The index doesn't need to be corrected for the small compressed texture workaround
- // because a rendertarget is never compressed.
- unsetConflictingSRVs(gl::SAMPLER_VERTEX, depthStencilResource, index);
- unsetConflictingSRVs(gl::SAMPLER_PIXEL, depthStencilResource, index);
+ continue;
}
+
+ Buffer11 *bufferStorage = GetImplAs<Buffer11>(uniformBuffer.get());
+ const d3d11::Buffer *constantBuffer = nullptr;
+ UINT firstConstant = 0;
+ UINT numConstants = 0;
+
+ ANGLE_TRY(bufferStorage->getConstantBufferRange(context, uniformBufferOffset,
+ uniformBufferSize, &constantBuffer,
+ &firstConstant, &numConstants));
+
+ ASSERT(constantBuffer);
+
+ if (mCurrentConstantBufferPS[bufferIndex] == constantBuffer->getSerial() &&
+ mCurrentConstantBufferPSOffset[bufferIndex] == uniformBufferOffset &&
+ mCurrentConstantBufferPSSize[bufferIndex] == uniformBufferSize)
+ {
+ continue;
+ }
+
+ unsigned int appliedIndex = reservedFragment + static_cast<unsigned int>(bufferIndex);
+
+ if (firstConstant != 0 && uniformBufferSize != 0)
+ {
+ deviceContext1->PSSetConstantBuffers1(appliedIndex, 1, constantBuffer->getPointer(),
+ &firstConstant, &numConstants);
+ }
+ else
+ {
+ deviceContext->PSSetConstantBuffers(appliedIndex, 1, constantBuffer->getPointer());
+ }
+
+ mCurrentConstantBufferPS[appliedIndex] = constantBuffer->getSerial();
+ mCurrentConstantBufferPSOffset[appliedIndex] = uniformBufferOffset;
+ mCurrentConstantBufferPSSize[appliedIndex] = uniformBufferSize;
}
- if (setRenderTargets(framebufferRTVs, framebufferDSV))
+ return gl::NoError();
+}
+
+gl::Error StateManager11::syncTransformFeedbackBuffers(const gl::Context *context)
+{
+ const auto &glState = context->getGLState();
+
+ ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
+
+ // If transform feedback is not active, unbind all buffers
+ if (!glState.isTransformFeedbackActiveUnpaused())
{
- setViewportBounds(renderTargetWidth, renderTargetHeight);
+ if (mAppliedTFSerial != mEmptySerial)
+ {
+ deviceContext->SOSetTargets(0, nullptr, nullptr);
+ mAppliedTFSerial = mEmptySerial;
+ }
+ return gl::NoError();
}
- gl::Error error = framebuffer11->invalidateSwizzles();
- if (error.isError())
+ gl::TransformFeedback *transformFeedback = glState.getCurrentTransformFeedback();
+ TransformFeedback11 *tf11 = GetImplAs<TransformFeedback11>(transformFeedback);
+ if (mAppliedTFSerial == tf11->getSerial() && !tf11->isDirty())
{
- return error;
+ return gl::NoError();
}
- return gl::Error(GL_NO_ERROR);
+ const std::vector<ID3D11Buffer *> *soBuffers = nullptr;
+ ANGLE_TRY_RESULT(tf11->getSOBuffers(context), soBuffers);
+ const std::vector<UINT> &soOffsets = tf11->getSOBufferOffsets();
+
+ deviceContext->SOSetTargets(tf11->getNumSOBuffers(), soBuffers->data(), soOffsets.data());
+
+ mAppliedTFSerial = tf11->getSerial();
+ tf11->onApply();
+
+ return gl::NoError();
+}
+
+// DrawCallVertexParams implementation.
+DrawCallVertexParams::DrawCallVertexParams(GLint firstVertex,
+ GLsizei vertexCount,
+ GLsizei instances)
+ : mHasIndexRange(nullptr),
+ mFirstVertex(firstVertex),
+ mVertexCount(vertexCount),
+ mInstances(instances),
+ mBaseVertex(0)
+{
+}
+
+// Use when in a drawElements call.
+DrawCallVertexParams::DrawCallVertexParams(bool firstVertexDefinitelyZero,
+ const gl::HasIndexRange &hasIndexRange,
+ GLint baseVertex,
+ GLsizei instances)
+ : mHasIndexRange(&hasIndexRange),
+ mFirstVertex(),
+ mVertexCount(0),
+ mInstances(instances),
+ mBaseVertex(baseVertex)
+{
+ if (firstVertexDefinitelyZero)
+ {
+ mFirstVertex = baseVertex;
+ }
+}
+
+GLint DrawCallVertexParams::firstVertex() const
+{
+ if (!mFirstVertex.valid())
+ {
+ ensureResolved();
+ ASSERT(mFirstVertex.valid());
+ }
+ return mFirstVertex.value();
+}
+
+GLsizei DrawCallVertexParams::vertexCount() const
+{
+ ensureResolved();
+ return mVertexCount;
+}
+
+GLsizei DrawCallVertexParams::instances() const
+{
+ return mInstances;
+}
+
+void DrawCallVertexParams::ensureResolved() const
+{
+ if (mHasIndexRange)
+ {
+ ASSERT(!mFirstVertex.valid() || mFirstVertex == mBaseVertex);
+
+ // Resolve the index range now if we need to.
+ const auto &indexRange = mHasIndexRange->getIndexRange().value();
+ mFirstVertex = mBaseVertex + static_cast<GLint>(indexRange.start);
+ mVertexCount = static_cast<GLsizei>(indexRange.vertexCount());
+ mHasIndexRange = nullptr;
+ }
}
} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/StateManager11.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/StateManager11.h
index f900882d7e..e48bc83a22 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/StateManager11.h
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/StateManager11.h
@@ -11,12 +11,15 @@
#include <array>
-#include "libANGLE/angletypes.h"
-#include "libANGLE/Data.h"
+#include "libANGLE/ContextState.h"
#include "libANGLE/State.h"
+#include "libANGLE/angletypes.h"
+#include "libANGLE/renderer/d3d/IndexDataManager.h"
+#include "libANGLE/renderer/d3d/RendererD3D.h"
+#include "libANGLE/renderer/d3d/d3d11/InputLayoutCache.h"
+#include "libANGLE/renderer/d3d/d3d11/Query11.h"
#include "libANGLE/renderer/d3d/d3d11/RenderStateCache.h"
#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
-#include "libANGLE/renderer/d3d/RendererD3D.h"
namespace rx
{
@@ -24,20 +27,147 @@ namespace rx
struct RenderTargetDesc;
struct Renderer11DeviceCaps;
-struct dx_VertexConstants11
+class ShaderConstants11 : angle::NonCopyable
{
- float depthRange[4];
- float viewAdjust[4];
- float viewCoords[4];
- float viewScale[4];
+ public:
+ ShaderConstants11();
+ ~ShaderConstants11();
+
+ void init(const gl::Caps &caps);
+ size_t getRequiredBufferSize(gl::SamplerType samplerType) const;
+ void markDirty();
+
+ void setComputeWorkGroups(GLuint numGroupsX, GLuint numGroupsY, GLuint numGroupsZ);
+ void setMultiviewWriteToViewportIndex(GLfloat index);
+ void onViewportChange(const gl::Rectangle &glViewport,
+ const D3D11_VIEWPORT &dxViewport,
+ bool is9_3,
+ bool presentPathFast);
+ void onSamplerChange(gl::SamplerType samplerType,
+ unsigned int samplerIndex,
+ const gl::Texture &texture);
+
+ gl::Error updateBuffer(ID3D11DeviceContext *deviceContext,
+ gl::SamplerType samplerType,
+ const ProgramD3D &programD3D,
+ const d3d11::Buffer &driverConstantBuffer);
+
+ private:
+ struct Vertex
+ {
+ Vertex()
+ : depthRange{.0f},
+ viewAdjust{.0f},
+ viewCoords{.0f},
+ viewScale{.0f},
+ multiviewWriteToViewportIndex{.0f},
+ padding{.0f}
+ {
+ }
+
+ float depthRange[4];
+ float viewAdjust[4];
+ float viewCoords[4];
+ float viewScale[2];
+ // multiviewWriteToViewportIndex is used to select either the side-by-side or layered
+ // code-path in the GS. It's value, if set, is either 0.0f or 1.0f. The value is updated
+ // whenever a multi-view draw framebuffer is made active.
+ float multiviewWriteToViewportIndex;
+
+ // Added here to manually pad the struct.
+ float padding;
+ };
+
+ struct Pixel
+ {
+ Pixel()
+ : depthRange{.0f},
+ viewCoords{.0f},
+ depthFront{.0f},
+ viewScale{.0f},
+ multiviewWriteToViewportIndex(0),
+ padding(0)
+ {
+ }
+
+ float depthRange[4];
+ float viewCoords[4];
+ float depthFront[4];
+ float viewScale[2];
+ // multiviewWriteToViewportIndex is used to select either the side-by-side or layered
+ // code-path in the GS. It's value, if set, is either 0.0f or 1.0f. The value is updated
+ // whenever a multi-view draw framebuffer is made active.
+ float multiviewWriteToViewportIndex;
+
+ // Added here to manually pad the struct.
+ float padding;
+ };
+
+ struct Compute
+ {
+ Compute() : numWorkGroups{0u}, padding(0u) {}
+ unsigned int numWorkGroups[3];
+ unsigned int padding; // This just pads the struct to 16 bytes
+ };
+
+ struct SamplerMetadata
+ {
+ SamplerMetadata() : baseLevel(0), internalFormatBits(0), wrapModes(0), padding(0) {}
+
+ int baseLevel;
+ int internalFormatBits;
+ int wrapModes;
+ int padding; // This just pads the struct to 16 bytes
+ };
+
+ static_assert(sizeof(SamplerMetadata) == 16u,
+ "Sampler metadata struct must be one 4-vec / 16 bytes.");
+
+ // Return true if dirty.
+ bool updateSamplerMetadata(SamplerMetadata *data, const gl::Texture &texture);
+
+ Vertex mVertex;
+ bool mVertexDirty;
+ Pixel mPixel;
+ bool mPixelDirty;
+ Compute mCompute;
+ bool mComputeDirty;
+
+ std::vector<SamplerMetadata> mSamplerMetadataVS;
+ bool mSamplerMetadataVSDirty;
+ std::vector<SamplerMetadata> mSamplerMetadataPS;
+ bool mSamplerMetadataPSDirty;
+ std::vector<SamplerMetadata> mSamplerMetadataCS;
+ bool mSamplerMetadataCSDirty;
};
-struct dx_PixelConstants11
+class DrawCallVertexParams final : angle::NonCopyable
{
- float depthRange[4];
- float viewCoords[4];
- float depthFront[4];
- float viewScale[4];
+ public:
+ // Use when in a drawArrays call.
+ DrawCallVertexParams(GLint firstVertex, GLsizei vertexCount, GLsizei instances);
+
+ // Use when in a drawElements call.
+ DrawCallVertexParams(bool firstVertexDefinitelyZero,
+ const gl::HasIndexRange &hasIndexRange,
+ GLint baseVertex,
+ GLsizei instances);
+
+ // It should be possible to also use an overload to handle the 'slow' indirect draw path.
+ // TODO(jmadill): Indirect draw slow path overload.
+
+ GLint firstVertex() const;
+ GLsizei vertexCount() const;
+ GLsizei instances() const;
+
+ private:
+ void ensureResolved() const;
+
+ mutable const gl::HasIndexRange *mHasIndexRange;
+ mutable Optional<GLint> mFirstVertex;
+ mutable GLsizei mVertexCount;
+ GLsizei mInstances;
+ GLint mBaseVertex;
};
class StateManager11 final : angle::NonCopyable
@@ -46,62 +176,221 @@ class StateManager11 final : angle::NonCopyable
StateManager11(Renderer11 *renderer);
~StateManager11();
- void initialize(const gl::Caps &caps);
- void syncState(const gl::State &state, const gl::State::DirtyBits &dirtyBits);
+ gl::Error initialize(const gl::Caps &caps, const gl::Extensions &extensions);
+ void deinitialize();
- gl::Error setBlendState(const gl::Framebuffer *framebuffer,
- const gl::BlendState &blendState,
- const gl::ColorF &blendColor,
- unsigned int sampleMask);
+ void syncState(const gl::Context *context, const gl::State::DirtyBits &dirtyBits);
- gl::Error setDepthStencilState(const gl::State &glState);
+ gl::Error updateStateForCompute(const gl::Context *context,
+ GLuint numGroupsX,
+ GLuint numGroupsY,
+ GLuint numGroupsZ);
- gl::Error setRasterizerState(const gl::RasterizerState &rasterState);
+ void updateStencilSizeIfChanged(bool depthStencilInitialized, unsigned int stencilSize);
- void setScissorRectangle(const gl::Rectangle &scissor, bool enabled);
+ // These invalidations methods are called externally.
- void setViewport(const gl::Caps *caps, const gl::Rectangle &viewport, float zNear, float zFar);
+ // Called from TextureStorage11.
+ void invalidateBoundViews();
- void updatePresentPath(bool presentPathFastActive,
- const gl::FramebufferAttachment *framebufferAttachment);
+ // Called from VertexArray11::updateVertexAttribStorage.
+ void invalidateCurrentValueAttrib(size_t attribIndex);
- const dx_VertexConstants11 &getVertexConstants() const { return mVertexConstants; }
- const dx_PixelConstants11 &getPixelConstants() const { return mPixelConstants; }
+ // Checks are done on a framebuffer state change to trigger other state changes.
+ // The Context is allowed to be nullptr for these methods, when called in EGL init code.
+ void invalidateRenderTarget();
- void updateStencilSizeIfChanged(bool depthStencilInitialized, unsigned int stencilSize);
+ // Called by instanced point sprite emulation.
+ void invalidateVertexBuffer();
+
+ // Called by Framebuffer11::syncState for the default sized viewport.
+ void invalidateViewport(const gl::Context *context);
+
+ // Called by TextureStorage11::markLevelDirty.
+ void invalidateSwizzles();
+
+ // Called by the Framebuffer11 and VertexArray11.
+ void invalidateShaders();
+ // Called by VertexArray11 to trigger attribute translation.
+ void invalidateVertexAttributeTranslation();
+
+ void setRenderTarget(ID3D11RenderTargetView *rtv, ID3D11DepthStencilView *dsv);
+ void setRenderTargets(ID3D11RenderTargetView **rtvs, UINT numRtvs, ID3D11DepthStencilView *dsv);
+
+ void onBeginQuery(Query11 *query);
+ void onDeleteQueryObject(Query11 *query);
+ gl::Error onMakeCurrent(const gl::Context *context);
+
+ void setInputLayout(const d3d11::InputLayout *inputLayout);
+
+ // TODO(jmadill): Migrate to d3d11::Buffer.
+ bool queueVertexBufferChange(size_t bufferIndex,
+ ID3D11Buffer *buffer,
+ UINT stride,
+ UINT offset);
+ bool queueVertexOffsetChange(size_t bufferIndex, UINT offsetOnly);
+ void applyVertexBufferChanges();
+
+ void setSingleVertexBuffer(const d3d11::Buffer *buffer, UINT stride, UINT offset);
+
+ gl::Error updateState(const gl::Context *context, GLenum drawMode);
+
+ void setShaderResourceShared(gl::SamplerType shaderType,
+ UINT resourceSlot,
+ const d3d11::SharedSRV *srv);
void setShaderResource(gl::SamplerType shaderType,
UINT resourceSlot,
- ID3D11ShaderResourceView *srv);
+ const d3d11::ShaderResourceView *srv);
+ void setPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY primitiveTopology);
+
+ void setDrawShaders(const d3d11::VertexShader *vertexShader,
+ const d3d11::GeometryShader *geometryShader,
+ const d3d11::PixelShader *pixelShader);
+ void setVertexShader(const d3d11::VertexShader *shader);
+ void setGeometryShader(const d3d11::GeometryShader *shader);
+ void setPixelShader(const d3d11::PixelShader *shader);
+ void setComputeShader(const d3d11::ComputeShader *shader);
+ void setVertexConstantBuffer(unsigned int slot, const d3d11::Buffer *buffer);
+ void setPixelConstantBuffer(unsigned int slot, const d3d11::Buffer *buffer);
+ void setDepthStencilState(const d3d11::DepthStencilState *depthStencilState, UINT stencilRef);
+ void setSimpleBlendState(const d3d11::BlendState *blendState);
+ void setRasterizerState(const d3d11::RasterizerState *rasterizerState);
+ void setSimpleViewport(const gl::Extents &viewportExtents);
+ void setSimpleViewport(int width, int height);
+ void setSimplePixelTextureAndSampler(const d3d11::SharedSRV &srv,
+ const d3d11::SamplerState &samplerState);
+ void setSimpleScissorRect(const gl::Rectangle &glRect);
+ void setScissorRectD3D(const D3D11_RECT &d3dRect);
+
+ // Not handled by an internal dirty bit because of the extra draw parameters.
+ gl::Error applyVertexBuffer(const gl::Context *context,
+ GLenum mode,
+ const DrawCallVertexParams &vertexParams,
+ bool isIndexedRendering);
+
+ gl::Error applyIndexBuffer(const gl::Context *context,
+ const void *indices,
+ GLsizei count,
+ GLenum type,
+ const gl::HasIndexRange &lazyIndexRange,
+ bool usePrimitiveRestartWorkaround);
+
+ void setIndexBuffer(ID3D11Buffer *buffer, DXGI_FORMAT indexFormat, unsigned int offset);
+
+ gl::Error updateVertexOffsetsForPointSpritesEmulation(GLint startVertex,
+ GLsizei emulatedInstanceId);
+
+ // TODO(jmadill): Should be private.
+ gl::Error applyComputeUniforms(ProgramD3D *programD3D);
+
+ // Only used in testing.
+ InputLayoutCache *getInputLayoutCache() { return &mInputLayoutCache; }
+
+ private:
+ template <typename SRVType>
+ void setShaderResourceInternal(gl::SamplerType shaderType,
+ UINT resourceSlot,
+ const SRVType *srv);
+
+ bool unsetConflictingView(ID3D11View *view);
+ bool unsetConflictingSRVs(gl::SamplerType shaderType,
+ uintptr_t resource,
+ const gl::ImageIndex *index);
+ void unsetConflictingAttachmentResources(const gl::FramebufferAttachment *attachment,
+ ID3D11Resource *resource);
+
+ gl::Error syncBlendState(const gl::Context *context,
+ const gl::Framebuffer *framebuffer,
+ const gl::BlendState &blendState,
+ const gl::ColorF &blendColor,
+ unsigned int sampleMask);
+
+ gl::Error syncDepthStencilState(const gl::State &glState);
+
+ gl::Error syncRasterizerState(const gl::Context *context, bool pointDrawMode);
+
+ void syncScissorRectangle(const gl::Rectangle &scissor, bool enabled);
+
+ void syncViewport(const gl::Context *context);
+
+ void checkPresentPath(const gl::Context *context);
+
+ gl::Error syncFramebuffer(const gl::Context *context, gl::Framebuffer *framebuffer);
+ gl::Error syncProgram(const gl::Context *context, GLenum drawMode);
+
+ gl::Error syncTextures(const gl::Context *context);
+ gl::Error applyTextures(const gl::Context *context, gl::SamplerType shaderType);
+
+ gl::Error setSamplerState(const gl::Context *context,
+ gl::SamplerType type,
+ int index,
+ gl::Texture *texture,
+ const gl::SamplerState &sampler);
+ gl::Error setTexture(const gl::Context *context,
+ gl::SamplerType type,
+ int index,
+ gl::Texture *texture);
+
+ // Faster than calling setTexture a jillion times
gl::Error clearTextures(gl::SamplerType samplerType, size_t rangeStart, size_t rangeEnd);
+ void handleMultiviewDrawFramebufferChange(const gl::Context *context);
- gl::Error syncFramebuffer(const gl::Framebuffer *framebuffer);
+ gl::Error syncCurrentValueAttribs(const gl::State &glState);
- void invalidateRenderTarget();
- void invalidateEverything();
- bool setRenderTargets(const RenderTargetArray &renderTargets,
- ID3D11DepthStencilView *depthStencil);
- void setRenderTarget(ID3D11RenderTargetView *renderTarget,
- ID3D11DepthStencilView *depthStencil);
+ gl::Error generateSwizzle(const gl::Context *context, gl::Texture *texture);
+ gl::Error generateSwizzlesForShader(const gl::Context *context, gl::SamplerType type);
+ gl::Error generateSwizzles(const gl::Context *context);
- private:
- void unsetConflictingSRVs(gl::SamplerType shaderType,
- uintptr_t resource,
- const gl::ImageIndex &index);
- void setViewportBounds(const int width, const int height);
+ gl::Error applyDriverUniforms(const ProgramD3D &programD3D);
+ gl::Error applyUniforms(ProgramD3D *programD3D);
+
+ gl::Error syncUniformBuffers(const gl::Context *context, ProgramD3D *programD3D);
+ gl::Error syncTransformFeedbackBuffers(const gl::Context *context);
+
+ // These are currently only called internally.
+ void invalidateTexturesAndSamplers();
+ void invalidateDriverUniforms();
+ void invalidateProgramUniforms();
+ void invalidateProgramUniformBuffers();
+ void invalidateConstantBuffer(unsigned int slot);
+
+ // Called by the Framebuffer11 directly.
+ void processFramebufferInvalidation(const gl::Context *context);
+
+ bool syncIndexBuffer(ID3D11Buffer *buffer, DXGI_FORMAT indexFormat, unsigned int offset);
+
+ enum DirtyBitType
+ {
+ DIRTY_BIT_RENDER_TARGET,
+ DIRTY_BIT_VIEWPORT_STATE,
+ DIRTY_BIT_SCISSOR_STATE,
+ DIRTY_BIT_RASTERIZER_STATE,
+ DIRTY_BIT_BLEND_STATE,
+ DIRTY_BIT_DEPTH_STENCIL_STATE,
+ DIRTY_BIT_TEXTURE_AND_SAMPLER_STATE,
+ DIRTY_BIT_PROGRAM_UNIFORMS,
+ DIRTY_BIT_DRIVER_UNIFORMS,
+ DIRTY_BIT_PROGRAM_UNIFORM_BUFFERS,
+ DIRTY_BIT_SHADERS,
+ DIRTY_BIT_CURRENT_VALUE_ATTRIBS,
+ DIRTY_BIT_INVALID,
+ DIRTY_BIT_MAX = DIRTY_BIT_INVALID,
+ };
+
+ using DirtyBits = angle::BitSet<DIRTY_BIT_MAX>;
Renderer11 *mRenderer;
+ // Internal dirty bits.
+ DirtyBits mInternalDirtyBits;
+
// Blend State
- bool mBlendStateIsDirty;
- // TODO(dianx) temporary representation of a dirty bit. once we move enough states in,
- // try experimenting with dirty bit instead of a bool
gl::BlendState mCurBlendState;
gl::ColorF mCurBlendColor;
unsigned int mCurSampleMask;
// Currently applied depth stencil state
- bool mDepthStencilStateIsDirty;
gl::DepthStencilState mCurDepthStencilState;
int mCurStencilRef;
int mCurStencilBackRef;
@@ -110,34 +399,35 @@ class StateManager11 final : angle::NonCopyable
Optional<bool> mCurDisableStencil;
// Currently applied rasterizer state
- bool mRasterizerStateIsDirty;
gl::RasterizerState mCurRasterState;
// Currently applied scissor rectangle state
- bool mScissorStateIsDirty;
bool mCurScissorEnabled;
gl::Rectangle mCurScissorRect;
// Currently applied viewport state
- bool mViewportStateIsDirty;
gl::Rectangle mCurViewport;
float mCurNear;
float mCurFar;
+ // The viewport offsets are guaranteed to be updated whenever the gl::State::DirtyBits are
+ // resolved and can be applied to the viewport and scissor whenever the internal viewport and
+ // scissor bits are resolved.
+ std::vector<gl::Offset> mViewportOffsets;
+
// Things needed in viewport state
- dx_VertexConstants11 mVertexConstants;
- dx_PixelConstants11 mPixelConstants;
+ ShaderConstants11 mShaderConstants;
// Render target variables
gl::Extents mViewportBounds;
+ bool mRenderTargetIsDirty;
// EGL_ANGLE_experimental_present_path variables
bool mCurPresentPathFastEnabled;
int mCurPresentPathFastColorBufferHeight;
- // Current RenderTarget state
- std::array<uintptr_t, gl::IMPLEMENTATION_MAX_DRAW_BUFFERS> mAppliedRTVs;
- uintptr_t mAppliedDSV;
+ // Queries that are currently active in this state
+ std::set<Query11 *> mCurrentQueries;
// Currently applied textures
struct SRVRecord
@@ -154,7 +444,8 @@ class StateManager11 final : angle::NonCopyable
class SRVCache : angle::NonCopyable
{
public:
- SRVCache() : mHighestUsedSRV(0) {}
+ SRVCache();
+ ~SRVCache();
void initialize(size_t size) { mCurrentSRVs.resize(size); }
@@ -175,6 +466,91 @@ class StateManager11 final : angle::NonCopyable
// A block of NULL pointers, cached so we don't re-allocate every draw call
std::vector<ID3D11ShaderResourceView *> mNullSRVs;
+
+ // Current translations of "Current-Value" data - owned by Context, not VertexArray.
+ gl::AttributesMask mDirtyCurrentValueAttribs;
+ std::vector<TranslatedAttribute> mCurrentValueAttribs;
+
+ // Current applied input layout.
+ ResourceSerial mCurrentInputLayout;
+ bool mInputLayoutIsDirty;
+ bool mVertexAttribsNeedTranslation;
+
+ // Current applied vertex states.
+ // TODO(jmadill): Figure out how to use ResourceSerial here.
+ std::array<ID3D11Buffer *, gl::MAX_VERTEX_ATTRIBS> mCurrentVertexBuffers;
+ std::array<UINT, gl::MAX_VERTEX_ATTRIBS> mCurrentVertexStrides;
+ std::array<UINT, gl::MAX_VERTEX_ATTRIBS> mCurrentVertexOffsets;
+ gl::RangeUI mDirtyVertexBufferRange;
+
+ // Currently applied primitive topology
+ D3D11_PRIMITIVE_TOPOLOGY mCurrentPrimitiveTopology;
+
+ // Currently applied shaders
+ ResourceSerial mAppliedVertexShader;
+ ResourceSerial mAppliedGeometryShader;
+ ResourceSerial mAppliedPixelShader;
+ ResourceSerial mAppliedComputeShader;
+
+ // Currently applied sampler states
+ std::vector<bool> mForceSetVertexSamplerStates;
+ std::vector<gl::SamplerState> mCurVertexSamplerStates;
+
+ std::vector<bool> mForceSetPixelSamplerStates;
+ std::vector<gl::SamplerState> mCurPixelSamplerStates;
+
+ std::vector<bool> mForceSetComputeSamplerStates;
+ std::vector<gl::SamplerState> mCurComputeSamplerStates;
+
+ // Special dirty bit for swizzles. Since they use internal shaders, must be done in a pre-pass.
+ bool mDirtySwizzles;
+
+ // Currently applied index buffer
+ ID3D11Buffer *mAppliedIB;
+ DXGI_FORMAT mAppliedIBFormat;
+ unsigned int mAppliedIBOffset;
+ bool mIndexBufferIsDirty;
+
+ // Vertex, index and input layouts
+ VertexDataManager mVertexDataManager;
+ IndexDataManager mIndexDataManager;
+ InputLayoutCache mInputLayoutCache;
+ std::vector<const TranslatedAttribute *> mCurrentAttributes;
+ Optional<GLint> mLastFirstVertex;
+
+ // ANGLE_multiview.
+ bool mIsMultiviewEnabled;
+
+ // Driver Constants.
+ d3d11::Buffer mDriverConstantBufferVS;
+ d3d11::Buffer mDriverConstantBufferPS;
+ d3d11::Buffer mDriverConstantBufferCS;
+
+ ResourceSerial mCurrentComputeConstantBuffer;
+ ResourceSerial mCurrentGeometryConstantBuffer;
+
+ template <typename T>
+ using VertexConstantBufferArray =
+ std::array<T, gl::IMPLEMENTATION_MAX_VERTEX_SHADER_UNIFORM_BUFFERS>;
+
+ VertexConstantBufferArray<ResourceSerial> mCurrentConstantBufferVS;
+ VertexConstantBufferArray<GLintptr> mCurrentConstantBufferVSOffset;
+ VertexConstantBufferArray<GLsizeiptr> mCurrentConstantBufferVSSize;
+
+ template <typename T>
+ using FragmentConstantBufferArray =
+ std::array<T, gl::IMPLEMENTATION_MAX_FRAGMENT_SHADER_UNIFORM_BUFFERS>;
+
+ FragmentConstantBufferArray<ResourceSerial> mCurrentConstantBufferPS;
+ FragmentConstantBufferArray<GLintptr> mCurrentConstantBufferPSOffset;
+ FragmentConstantBufferArray<GLsizeiptr> mCurrentConstantBufferPSSize;
+
+ // Currently applied transform feedback buffers
+ Serial mAppliedTFSerial;
+
+ Serial mEmptySerial;
+
+ bool mIsTransformFeedbackCurrentlyActiveUnpaused;
};
} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/StreamProducerNV12.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/StreamProducerNV12.cpp
new file mode 100644
index 0000000000..1981b5f7b2
--- /dev/null
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/StreamProducerNV12.cpp
@@ -0,0 +1,102 @@
+//
+// Copyright (c) 2016 The ANGLE Project Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+//
+
+// StreamProducerNV12.cpp: Implements the stream producer for NV12 textures
+
+#include "libANGLE/renderer/d3d/d3d11/StreamProducerNV12.h"
+
+#include "common/utilities.h"
+#include "libANGLE/renderer/d3d/d3d11/Renderer11.h"
+#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
+
+namespace rx
+{
+
+StreamProducerNV12::StreamProducerNV12(Renderer11 *renderer)
+ : mRenderer(renderer), mTexture(nullptr), mArraySlice(0), mTextureWidth(0), mTextureHeight(0)
+{
+}
+
+StreamProducerNV12::~StreamProducerNV12()
+{
+ SafeRelease(mTexture);
+}
+
+egl::Error StreamProducerNV12::validateD3DNV12Texture(void *pointer) const
+{
+ ID3D11Texture2D *textureD3D = static_cast<ID3D11Texture2D *>(pointer);
+
+ // Check that the texture originated from our device
+ ID3D11Device *device;
+ textureD3D->GetDevice(&device);
+ if (device != mRenderer->getDevice())
+ {
+ return egl::EglBadParameter() << "Texture not created on ANGLE D3D device";
+ }
+
+ // Get the description and validate it
+ D3D11_TEXTURE2D_DESC desc;
+ textureD3D->GetDesc(&desc);
+ if (desc.Format != DXGI_FORMAT_NV12)
+ {
+ return egl::EglBadParameter() << "Texture format not DXGI_FORMAT_NV12";
+ }
+ if (desc.Width < 1 || desc.Height < 1)
+ {
+ return egl::EglBadParameter() << "Texture is of size 0";
+ }
+ if ((desc.Width % 2) != 0 || (desc.Height % 2) != 0)
+ {
+ return egl::EglBadParameter() << "Texture dimensions are not even";
+ }
+ return egl::NoError();
+}
+
+void StreamProducerNV12::postD3DNV12Texture(void *pointer, const egl::AttributeMap &attributes)
+{
+ ASSERT(pointer != nullptr);
+ ID3D11Texture2D *textureD3D = static_cast<ID3D11Texture2D *>(pointer);
+
+ // Check that the texture originated from our device
+ ID3D11Device *device;
+ textureD3D->GetDevice(&device);
+
+ // Get the description
+ D3D11_TEXTURE2D_DESC desc;
+ textureD3D->GetDesc(&desc);
+
+ // Release the previous texture if there is one
+ SafeRelease(mTexture);
+
+ mTexture = textureD3D;
+ mTexture->AddRef();
+ mTextureWidth = desc.Width;
+ mTextureHeight = desc.Height;
+ mArraySlice = static_cast<UINT>(attributes.get(EGL_D3D_TEXTURE_SUBRESOURCE_ID_ANGLE, 0));
+}
+
+egl::Stream::GLTextureDescription StreamProducerNV12::getGLFrameDescription(int planeIndex)
+{
+ // The UV plane of NV12 textures has half the width/height of the Y plane
+ egl::Stream::GLTextureDescription desc;
+ desc.width = (planeIndex == 0) ? mTextureWidth : (mTextureWidth / 2);
+ desc.height = (planeIndex == 0) ? mTextureHeight : (mTextureHeight / 2);
+ desc.internalFormat = (planeIndex == 0) ? GL_R8 : GL_RG8;
+ desc.mipLevels = 0;
+ return desc;
+}
+
+ID3D11Texture2D *StreamProducerNV12::getD3DTexture()
+{
+ return mTexture;
+}
+
+UINT StreamProducerNV12::getArraySlice()
+{
+ return mArraySlice;
+}
+
+} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/StreamProducerNV12.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/StreamProducerNV12.h
new file mode 100644
index 0000000000..304c9dfe53
--- /dev/null
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/StreamProducerNV12.h
@@ -0,0 +1,44 @@
+//
+// Copyright (c) 2016 The ANGLE Project Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+//
+
+// StreamProducerNV12.h: Interface for a NV12 texture stream producer
+
+#ifndef LIBANGLE_RENDERER_D3D_D3D11_STREAM11_H_
+#define LIBANGLE_RENDERER_D3D_D3D11_STREAM11_H_
+
+#include "libANGLE/renderer/StreamProducerImpl.h"
+
+namespace rx
+{
+class Renderer11;
+
+class StreamProducerNV12 : public StreamProducerImpl
+{
+ public:
+ StreamProducerNV12(Renderer11 *renderer);
+ ~StreamProducerNV12() override;
+
+ egl::Error validateD3DNV12Texture(void *pointer) const override;
+ void postD3DNV12Texture(void *pointer, const egl::AttributeMap &attributes) override;
+ egl::Stream::GLTextureDescription getGLFrameDescription(int planeIndex) override;
+
+ // Gets a pointer to the internal D3D texture
+ ID3D11Texture2D *getD3DTexture();
+
+ // Gets the slice index for the D3D texture that the frame is in
+ UINT getArraySlice();
+
+ private:
+ Renderer11 *mRenderer;
+
+ ID3D11Texture2D *mTexture;
+ UINT mArraySlice;
+ UINT mTextureWidth;
+ UINT mTextureHeight;
+};
+} // namespace rx
+
+#endif // LIBANGLE_RENDERER_D3D_D3D11_STREAM11_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/SwapChain11.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/SwapChain11.cpp
index 42c336c8cf..dcfd06484d 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/SwapChain11.cpp
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/SwapChain11.cpp
@@ -11,9 +11,9 @@
#include <EGL/eglext.h>
#include "libANGLE/features.h"
-#include "libANGLE/renderer/d3d/d3d11/formatutils11.h"
-#include "libANGLE/renderer/d3d/d3d11/NativeWindow.h"
+#include "libANGLE/renderer/d3d/d3d11/NativeWindow11.h"
#include "libANGLE/renderer/d3d/d3d11/Renderer11.h"
+#include "libANGLE/renderer/d3d/d3d11/formatutils11.h"
#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
#include "libANGLE/renderer/d3d/d3d11/texture_format_table.h"
#include "third_party/trace_event/trace_event.h"
@@ -21,6 +21,7 @@
// Precompiled shaders
#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthrough2d11vs.h"
#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgba2d11ps.h"
+#include "libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgba2dms11ps.h"
#ifdef ANGLE_ENABLE_KEYEDMUTEX
#define ANGLE_RESOURCE_SHARE_TYPE D3D11_RESOURCE_MISC_SHARED_KEYEDMUTEX
@@ -33,22 +34,30 @@ namespace rx
namespace
{
-bool NeedsOffscreenTexture(Renderer11 *renderer, NativeWindow nativeWindow, EGLint orientation)
+// To avoid overflow in QPC to Microseconds calculations, since we multiply
+// by kMicrosecondsPerSecond, then the QPC value should not exceed
+// (2^63 - 1) / 1E6. If it exceeds that threshold, we divide then multiply.
+static constexpr int64_t kQPCOverflowThreshold = 0x8637BD05AF7;
+static constexpr int64_t kMicrosecondsPerSecond = 1000000;
+
+bool NeedsOffscreenTexture(Renderer11 *renderer, NativeWindow11 *nativeWindow, EGLint orientation)
{
// We don't need an offscreen texture if either orientation = INVERT_Y,
// or present path fast is enabled and we're not rendering onto an offscreen surface.
return orientation != EGL_SURFACE_ORIENTATION_INVERT_Y_ANGLE &&
- !(renderer->presentPathFastEnabled() && nativeWindow.getNativeWindow());
+ !(renderer->presentPathFastEnabled() && nativeWindow->getNativeWindow());
}
} // anonymous namespace
SwapChain11::SwapChain11(Renderer11 *renderer,
- NativeWindow nativeWindow,
+ NativeWindow11 *nativeWindow,
HANDLE shareHandle,
+ IUnknown *d3dTexture,
GLenum backBufferFormat,
GLenum depthBufferFormat,
- EGLint orientation)
- : SwapChainD3D(nativeWindow, shareHandle, backBufferFormat, depthBufferFormat),
+ EGLint orientation,
+ EGLint samples)
+ : SwapChainD3D(shareHandle, d3dTexture, backBufferFormat, depthBufferFormat),
mRenderer(renderer),
mWidth(-1),
mHeight(-1),
@@ -56,33 +65,42 @@ SwapChain11::SwapChain11(Renderer11 *renderer,
mAppCreatedShareHandle(mShareHandle != nullptr),
mSwapInterval(0),
mPassThroughResourcesInit(false),
+ mNativeWindow(nativeWindow),
mFirstSwap(true),
mSwapChain(nullptr),
-#if defined(ANGLE_ENABLE_D3D11_1)
mSwapChain1(nullptr),
-#endif
mKeyedMutex(nullptr),
- mBackBufferTexture(nullptr),
- mBackBufferRTView(nullptr),
- mBackBufferSRView(nullptr),
+ mBackBufferTexture(),
+ mBackBufferRTView(),
+ mBackBufferSRView(),
mNeedsOffscreenTexture(NeedsOffscreenTexture(renderer, nativeWindow, orientation)),
- mOffscreenTexture(nullptr),
- mOffscreenRTView(nullptr),
- mOffscreenSRView(nullptr),
- mDepthStencilTexture(nullptr),
- mDepthStencilDSView(nullptr),
- mDepthStencilSRView(nullptr),
- mQuadVB(nullptr),
- mPassThroughSampler(nullptr),
- mPassThroughIL(nullptr),
- mPassThroughVS(nullptr),
- mPassThroughPS(nullptr),
- mPassThroughRS(nullptr),
+ mOffscreenTexture(),
+ mOffscreenRTView(),
+ mOffscreenSRView(),
+ mNeedsOffscreenTextureCopy(false),
+ mOffscreenTextureCopyForSRV(),
+ mDepthStencilTexture(),
+ mDepthStencilDSView(),
+ mDepthStencilSRView(),
+ mQuadVB(),
+ mPassThroughSampler(),
+ mPassThroughIL(),
+ mPassThroughVS(),
+ mPassThroughPS(),
+ mPassThroughRS(),
mColorRenderTarget(this, renderer, false),
- mDepthStencilRenderTarget(this, renderer, true)
+ mDepthStencilRenderTarget(this, renderer, true),
+ mEGLSamples(samples)
{
// Sanity check that if present path fast is active then we're using the default orientation
ASSERT(!mRenderer->presentPathFastEnabled() || orientation == 0);
+
+ // Get the performance counter
+ LARGE_INTEGER counterFreqency = {};
+ BOOL success = QueryPerformanceFrequency(&counterFreqency);
+ ASSERT(success);
+
+ mQPCFrequency = counterFreqency.QuadPart;
}
SwapChain11::~SwapChain11()
@@ -92,52 +110,56 @@ SwapChain11::~SwapChain11()
void SwapChain11::release()
{
-#if defined(ANGLE_ENABLE_D3D11_1)
+ // TODO(jmadill): Should probably signal that the RenderTarget is dirty.
+
SafeRelease(mSwapChain1);
-#endif
SafeRelease(mSwapChain);
SafeRelease(mKeyedMutex);
- SafeRelease(mBackBufferTexture);
- SafeRelease(mBackBufferRTView);
- SafeRelease(mBackBufferSRView);
- SafeRelease(mOffscreenTexture);
- SafeRelease(mOffscreenRTView);
- SafeRelease(mOffscreenSRView);
- SafeRelease(mDepthStencilTexture);
- SafeRelease(mDepthStencilDSView);
- SafeRelease(mDepthStencilSRView);
- SafeRelease(mQuadVB);
- SafeRelease(mPassThroughSampler);
- SafeRelease(mPassThroughIL);
- SafeRelease(mPassThroughVS);
- SafeRelease(mPassThroughPS);
- SafeRelease(mPassThroughRS);
+ mBackBufferTexture.reset();
+ mBackBufferRTView.reset();
+ mBackBufferSRView.reset();
+ mOffscreenTexture.reset();
+ mOffscreenRTView.reset();
+ mOffscreenSRView.reset();
+ mDepthStencilTexture.reset();
+ mDepthStencilDSView.reset();
+ mDepthStencilSRView.reset();
+ mQuadVB.reset();
+ mPassThroughSampler.reset();
+ mPassThroughIL.reset();
+ mPassThroughVS.reset();
+ mPassThroughPS.reset();
+ mPassThroughRS.reset();
if (!mAppCreatedShareHandle)
{
- mShareHandle = NULL;
+ mShareHandle = nullptr;
}
}
void SwapChain11::releaseOffscreenColorBuffer()
{
- SafeRelease(mOffscreenTexture);
- SafeRelease(mOffscreenRTView);
- SafeRelease(mOffscreenSRView);
+ mOffscreenTexture.reset();
+ mOffscreenRTView.reset();
+ mOffscreenSRView.reset();
+ mNeedsOffscreenTextureCopy = false;
+ mOffscreenTextureCopyForSRV.reset();
}
void SwapChain11::releaseOffscreenDepthBuffer()
{
- SafeRelease(mDepthStencilTexture);
- SafeRelease(mDepthStencilDSView);
- SafeRelease(mDepthStencilSRView);
+ mDepthStencilTexture.reset();
+ mDepthStencilDSView.reset();
+ mDepthStencilSRView.reset();
}
-EGLint SwapChain11::resetOffscreenBuffers(int backbufferWidth, int backbufferHeight)
+EGLint SwapChain11::resetOffscreenBuffers(const gl::Context *context,
+ int backbufferWidth,
+ int backbufferHeight)
{
if (mNeedsOffscreenTexture)
{
- EGLint result = resetOffscreenColorBuffer(backbufferWidth, backbufferHeight);
+ EGLint result = resetOffscreenColorBuffer(context, backbufferWidth, backbufferHeight);
if (result != EGL_SUCCESS)
{
return result;
@@ -156,117 +178,106 @@ EGLint SwapChain11::resetOffscreenBuffers(int backbufferWidth, int backbufferHei
return EGL_SUCCESS;
}
-EGLint SwapChain11::resetOffscreenColorBuffer(int backbufferWidth, int backbufferHeight)
+EGLint SwapChain11::resetOffscreenColorBuffer(const gl::Context *context,
+ int backbufferWidth,
+ int backbufferHeight)
{
ASSERT(mNeedsOffscreenTexture);
TRACE_EVENT0("gpu.angle", "SwapChain11::resetOffscreenTexture");
ID3D11Device *device = mRenderer->getDevice();
- ASSERT(device != NULL);
+ ASSERT(device != nullptr);
// D3D11 does not allow zero size textures
ASSERT(backbufferWidth >= 1);
ASSERT(backbufferHeight >= 1);
// Preserve the render target content
- ID3D11Texture2D *previousOffscreenTexture = mOffscreenTexture;
- if (previousOffscreenTexture)
- {
- previousOffscreenTexture->AddRef();
- }
+ TextureHelper11 previousOffscreenTexture(std::move(mOffscreenTexture));
const int previousWidth = mWidth;
const int previousHeight = mHeight;
releaseOffscreenColorBuffer();
- const d3d11::TextureFormat &backbufferFormatInfo = d3d11::GetTextureFormatInfo(mOffscreenRenderTargetFormat, mRenderer->getRenderer11DeviceCaps());
+ const d3d11::Format &backbufferFormatInfo =
+ d3d11::Format::Get(mOffscreenRenderTargetFormat, mRenderer->getRenderer11DeviceCaps());
+ D3D11_TEXTURE2D_DESC offscreenTextureDesc = {0};
- // If the app passed in a share handle, open the resource
- // See EGL_ANGLE_d3d_share_handle_client_buffer
- if (mAppCreatedShareHandle)
+ // If the app passed in a share handle or D3D texture, open the resource
+ // See EGL_ANGLE_d3d_share_handle_client_buffer and EGL_ANGLE_d3d_texture_client_buffer
+ if (mAppCreatedShareHandle || mD3DTexture != nullptr)
{
- ID3D11Resource *tempResource11;
- HRESULT result = device->OpenSharedResource(mShareHandle, __uuidof(ID3D11Resource), (void**)&tempResource11);
+ if (mAppCreatedShareHandle)
+ {
+ ID3D11Resource *tempResource11;
+ HRESULT result = device->OpenSharedResource(mShareHandle, __uuidof(ID3D11Resource),
+ (void **)&tempResource11);
+ ASSERT(SUCCEEDED(result));
- if (FAILED(result))
+ mOffscreenTexture.set(d3d11::DynamicCastComObject<ID3D11Texture2D>(tempResource11),
+ backbufferFormatInfo);
+ SafeRelease(tempResource11);
+ }
+ else if (mD3DTexture != nullptr)
{
- ERR("Failed to open the swap chain pbuffer share handle: %08lX", result);
- release();
- return EGL_BAD_PARAMETER;
+ mOffscreenTexture.set(d3d11::DynamicCastComObject<ID3D11Texture2D>(mD3DTexture),
+ backbufferFormatInfo);
}
-
- result = tempResource11->QueryInterface(__uuidof(ID3D11Texture2D), (void**)&mOffscreenTexture);
- SafeRelease(tempResource11);
-
- if (FAILED(result))
+ else
{
- ERR("Failed to query texture2d interface in pbuffer share handle: %08lX", result);
- release();
- return EGL_BAD_PARAMETER;
+ UNREACHABLE();
}
+ ASSERT(mOffscreenTexture.valid());
+ mOffscreenTexture.getDesc(&offscreenTextureDesc);
- // Validate offscreen texture parameters
- D3D11_TEXTURE2D_DESC offscreenTextureDesc = {0};
- mOffscreenTexture->GetDesc(&offscreenTextureDesc);
-
- if (offscreenTextureDesc.Width != (UINT)backbufferWidth ||
- offscreenTextureDesc.Height != (UINT)backbufferHeight ||
- offscreenTextureDesc.Format != backbufferFormatInfo.texFormat ||
- offscreenTextureDesc.MipLevels != 1 ||
- offscreenTextureDesc.ArraySize != 1)
+ // Fail if the offscreen texture is not renderable.
+ if ((offscreenTextureDesc.BindFlags & D3D11_BIND_RENDER_TARGET) == 0)
{
- ERR("Invalid texture parameters in the shared offscreen texture pbuffer");
+ ERR() << "Could not use provided offscreen texture, texture not renderable.";
release();
- return EGL_BAD_PARAMETER;
+ return EGL_BAD_SURFACE;
}
}
else
{
- const bool useSharedResource = !mNativeWindow.getNativeWindow() && mRenderer->getShareHandleSupport();
+ const bool useSharedResource =
+ !mNativeWindow->getNativeWindow() && mRenderer->getShareHandleSupport();
- D3D11_TEXTURE2D_DESC offscreenTextureDesc = {0};
offscreenTextureDesc.Width = backbufferWidth;
offscreenTextureDesc.Height = backbufferHeight;
- offscreenTextureDesc.Format = backbufferFormatInfo.texFormat;
+ offscreenTextureDesc.Format = backbufferFormatInfo.texFormat;
offscreenTextureDesc.MipLevels = 1;
offscreenTextureDesc.ArraySize = 1;
- offscreenTextureDesc.SampleDesc.Count = 1;
+ offscreenTextureDesc.SampleDesc.Count = getD3DSamples();
offscreenTextureDesc.SampleDesc.Quality = 0;
offscreenTextureDesc.Usage = D3D11_USAGE_DEFAULT;
offscreenTextureDesc.BindFlags = D3D11_BIND_RENDER_TARGET | D3D11_BIND_SHADER_RESOURCE;
offscreenTextureDesc.CPUAccessFlags = 0;
offscreenTextureDesc.MiscFlags = useSharedResource ? ANGLE_RESOURCE_SHARE_TYPE : 0;
- HRESULT result = device->CreateTexture2D(&offscreenTextureDesc, NULL, &mOffscreenTexture);
-
- if (FAILED(result))
+ gl::Error err = mRenderer->allocateTexture(offscreenTextureDesc, backbufferFormatInfo,
+ &mOffscreenTexture);
+ if (err.isError())
{
- ERR("Could not create offscreen texture: %08lX", result);
+ ERR() << "Could not create offscreen texture, " << err;
release();
-
- if (d3d11::isDeviceLostError(result))
- {
- return EGL_CONTEXT_LOST;
- }
- else
- {
- return EGL_BAD_ALLOC;
- }
+ return EGL_BAD_ALLOC;
}
- d3d11::SetDebugName(mOffscreenTexture, "Offscreen back buffer texture");
+ mOffscreenTexture.setDebugName("Offscreen back buffer texture");
// EGL_ANGLE_surface_d3d_texture_2d_share_handle requires that we store a share handle for the client
if (useSharedResource)
{
- IDXGIResource *offscreenTextureResource = NULL;
- result = mOffscreenTexture->QueryInterface(__uuidof(IDXGIResource), (void**)&offscreenTextureResource);
+ IDXGIResource *offscreenTextureResource = nullptr;
+ HRESULT result = mOffscreenTexture.get()->QueryInterface(
+ __uuidof(IDXGIResource), (void **)&offscreenTextureResource);
// Fall back to no share handle on failure
if (FAILED(result))
{
- ERR("Could not query offscreen texture resource: %08lX", result);
+ ERR() << "Could not query offscreen texture resource, " << gl::FmtHR(result);
}
else
{
@@ -275,36 +286,49 @@ EGLint SwapChain11::resetOffscreenColorBuffer(int backbufferWidth, int backbuffe
if (FAILED(result))
{
- mShareHandle = NULL;
- ERR("Could not get offscreen texture shared handle: %08lX", result);
+ mShareHandle = nullptr;
+ ERR() << "Could not get offscreen texture shared handle, " << gl::FmtHR(result);
}
}
}
}
// This may return null if the original texture was created without a keyed mutex.
- mKeyedMutex = d3d11::DynamicCastComObject<IDXGIKeyedMutex>(mOffscreenTexture);
+ mKeyedMutex = d3d11::DynamicCastComObject<IDXGIKeyedMutex>(mOffscreenTexture.get());
D3D11_RENDER_TARGET_VIEW_DESC offscreenRTVDesc;
- offscreenRTVDesc.Format = backbufferFormatInfo.rtvFormat;
- offscreenRTVDesc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE2D;
+ offscreenRTVDesc.Format = backbufferFormatInfo.rtvFormat;
+ offscreenRTVDesc.ViewDimension =
+ (mEGLSamples <= 1) ? D3D11_RTV_DIMENSION_TEXTURE2D : D3D11_RTV_DIMENSION_TEXTURE2DMS;
offscreenRTVDesc.Texture2D.MipSlice = 0;
- HRESULT result = device->CreateRenderTargetView(mOffscreenTexture, &offscreenRTVDesc, &mOffscreenRTView);
- ASSERT(SUCCEEDED(result));
- d3d11::SetDebugName(mOffscreenRTView, "Offscreen back buffer render target");
+ gl::Error err =
+ mRenderer->allocateResource(offscreenRTVDesc, mOffscreenTexture.get(), &mOffscreenRTView);
+ ASSERT(!err.isError());
+ mOffscreenRTView.setDebugName("Offscreen back buffer render target");
D3D11_SHADER_RESOURCE_VIEW_DESC offscreenSRVDesc;
- offscreenSRVDesc.Format = backbufferFormatInfo.srvFormat;
- offscreenSRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2D;
+ offscreenSRVDesc.Format = backbufferFormatInfo.srvFormat;
+ offscreenSRVDesc.ViewDimension =
+ (mEGLSamples <= 1) ? D3D11_SRV_DIMENSION_TEXTURE2D : D3D11_SRV_DIMENSION_TEXTURE2DMS;
offscreenSRVDesc.Texture2D.MostDetailedMip = 0;
offscreenSRVDesc.Texture2D.MipLevels = static_cast<UINT>(-1);
- result = device->CreateShaderResourceView(mOffscreenTexture, &offscreenSRVDesc, &mOffscreenSRView);
- ASSERT(SUCCEEDED(result));
- d3d11::SetDebugName(mOffscreenSRView, "Offscreen back buffer shader resource");
+ if (offscreenTextureDesc.BindFlags & D3D11_BIND_SHADER_RESOURCE)
+ {
+ err = mRenderer->allocateResource(offscreenSRVDesc, mOffscreenTexture.get(),
+ &mOffscreenSRView);
+ ASSERT(!err.isError());
+ mOffscreenSRView.setDebugName("Offscreen back buffer shader resource");
+ }
+ else
+ {
+ // Special case for external textures that cannot support sampling. Since internally we
+ // assume our SwapChain is always readable, we make a copy texture that is compatible.
+ mNeedsOffscreenTextureCopy = true;
+ }
- if (previousOffscreenTexture != nullptr)
+ if (previousOffscreenTexture.valid())
{
D3D11_BOX sourceBox = {0};
sourceBox.left = 0;
@@ -316,14 +340,12 @@ EGLint SwapChain11::resetOffscreenColorBuffer(int backbufferWidth, int backbuffe
ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
const int yoffset = std::max(backbufferHeight - previousHeight, 0);
- deviceContext->CopySubresourceRegion(mOffscreenTexture, 0, 0, yoffset, 0,
- previousOffscreenTexture, 0, &sourceBox);
-
- SafeRelease(previousOffscreenTexture);
+ deviceContext->CopySubresourceRegion(mOffscreenTexture.get(), 0, 0, yoffset, 0,
+ previousOffscreenTexture.get(), 0, &sourceBox);
if (mSwapChain)
{
- swapRect(0, 0, backbufferWidth, backbufferHeight);
+ swapRect(context, 0, 0, backbufferWidth, backbufferHeight);
}
}
@@ -336,21 +358,38 @@ EGLint SwapChain11::resetOffscreenDepthBuffer(int backbufferWidth, int backbuffe
if (mDepthBufferFormat != GL_NONE)
{
- const d3d11::TextureFormat &depthBufferFormatInfo =
- d3d11::GetTextureFormatInfo(mDepthBufferFormat, mRenderer->getRenderer11DeviceCaps());
+ const d3d11::Format &depthBufferFormatInfo =
+ d3d11::Format::Get(mDepthBufferFormat, mRenderer->getRenderer11DeviceCaps());
D3D11_TEXTURE2D_DESC depthStencilTextureDesc;
depthStencilTextureDesc.Width = backbufferWidth;
depthStencilTextureDesc.Height = backbufferHeight;
- depthStencilTextureDesc.Format = depthBufferFormatInfo.texFormat;
+ depthStencilTextureDesc.Format = depthBufferFormatInfo.texFormat;
depthStencilTextureDesc.MipLevels = 1;
depthStencilTextureDesc.ArraySize = 1;
- depthStencilTextureDesc.SampleDesc.Count = 1;
- depthStencilTextureDesc.SampleDesc.Quality = 0;
+ depthStencilTextureDesc.SampleDesc.Count = getD3DSamples();
depthStencilTextureDesc.Usage = D3D11_USAGE_DEFAULT;
depthStencilTextureDesc.BindFlags = D3D11_BIND_DEPTH_STENCIL;
- if (depthBufferFormatInfo.srvFormat != DXGI_FORMAT_UNKNOWN)
+ // If there is a multisampled offscreen color texture, the offscreen depth-stencil texture
+ // must also have the same quality value.
+ if (mOffscreenTexture.valid() && getD3DSamples() > 1)
+ {
+ D3D11_TEXTURE2D_DESC offscreenTextureDesc = {0};
+ mOffscreenTexture.getDesc(&offscreenTextureDesc);
+ depthStencilTextureDesc.SampleDesc.Quality = offscreenTextureDesc.SampleDesc.Quality;
+ }
+ else
+ {
+ depthStencilTextureDesc.SampleDesc.Quality = 0;
+ }
+
+ // Only create an SRV if it is supported
+ bool depthStencilSRV =
+ depthBufferFormatInfo.srvFormat != DXGI_FORMAT_UNKNOWN &&
+ (mRenderer->getRenderer11DeviceCaps().supportsMultisampledDepthStencilSRVs ||
+ depthStencilTextureDesc.SampleDesc.Count <= 1);
+ if (depthStencilSRV)
{
depthStencilTextureDesc.BindFlags |= D3D11_BIND_SHADER_RESOURCE;
}
@@ -358,58 +397,56 @@ EGLint SwapChain11::resetOffscreenDepthBuffer(int backbufferWidth, int backbuffe
depthStencilTextureDesc.CPUAccessFlags = 0;
depthStencilTextureDesc.MiscFlags = 0;
- ID3D11Device *device = mRenderer->getDevice();
- HRESULT result =
- device->CreateTexture2D(&depthStencilTextureDesc, NULL, &mDepthStencilTexture);
- if (FAILED(result))
+ gl::Error err = mRenderer->allocateTexture(depthStencilTextureDesc, depthBufferFormatInfo,
+ &mDepthStencilTexture);
+ if (err.isError())
{
- ERR("Could not create depthstencil surface for new swap chain: 0x%08X", result);
+ ERR() << "Could not create depthstencil surface for new swap chain, " << err;
release();
-
- if (d3d11::isDeviceLostError(result))
- {
- return EGL_CONTEXT_LOST;
- }
- else
- {
- return EGL_BAD_ALLOC;
- }
+ return EGL_BAD_ALLOC;
}
- d3d11::SetDebugName(mDepthStencilTexture, "Offscreen depth stencil texture");
+ mDepthStencilTexture.setDebugName("Offscreen depth stencil texture");
D3D11_DEPTH_STENCIL_VIEW_DESC depthStencilDesc;
- depthStencilDesc.Format = depthBufferFormatInfo.dsvFormat;
- depthStencilDesc.ViewDimension = D3D11_DSV_DIMENSION_TEXTURE2D;
+ depthStencilDesc.Format = depthBufferFormatInfo.dsvFormat;
+ depthStencilDesc.ViewDimension =
+ (mEGLSamples <= 1) ? D3D11_DSV_DIMENSION_TEXTURE2D : D3D11_DSV_DIMENSION_TEXTURE2DMS;
depthStencilDesc.Flags = 0;
depthStencilDesc.Texture2D.MipSlice = 0;
- result = device->CreateDepthStencilView(mDepthStencilTexture, &depthStencilDesc, &mDepthStencilDSView);
- ASSERT(SUCCEEDED(result));
- d3d11::SetDebugName(mDepthStencilDSView, "Offscreen depth stencil view");
+ err = mRenderer->allocateResource(depthStencilDesc, mDepthStencilTexture.get(),
+ &mDepthStencilDSView);
+ ASSERT(!err.isError());
+ mDepthStencilDSView.setDebugName("Offscreen depth stencil view");
- if (depthBufferFormatInfo.srvFormat != DXGI_FORMAT_UNKNOWN)
+ if (depthStencilSRV)
{
D3D11_SHADER_RESOURCE_VIEW_DESC depthStencilSRVDesc;
- depthStencilSRVDesc.Format = depthBufferFormatInfo.srvFormat;
- depthStencilSRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2D;
+ depthStencilSRVDesc.Format = depthBufferFormatInfo.srvFormat;
+ depthStencilSRVDesc.ViewDimension = (mEGLSamples <= 1)
+ ? D3D11_SRV_DIMENSION_TEXTURE2D
+ : D3D11_SRV_DIMENSION_TEXTURE2DMS;
depthStencilSRVDesc.Texture2D.MostDetailedMip = 0;
depthStencilSRVDesc.Texture2D.MipLevels = static_cast<UINT>(-1);
- result = device->CreateShaderResourceView(mDepthStencilTexture, &depthStencilSRVDesc, &mDepthStencilSRView);
- ASSERT(SUCCEEDED(result));
- d3d11::SetDebugName(mDepthStencilSRView, "Offscreen depth stencil shader resource");
+ err = mRenderer->allocateResource(depthStencilSRVDesc, mDepthStencilTexture.get(),
+ &mDepthStencilSRView);
+ ASSERT(!err.isError());
+ mDepthStencilSRView.setDebugName("Offscreen depth stencil shader resource");
}
}
return EGL_SUCCESS;
}
-EGLint SwapChain11::resize(EGLint backbufferWidth, EGLint backbufferHeight)
+EGLint SwapChain11::resize(const gl::Context *context,
+ EGLint backbufferWidth,
+ EGLint backbufferHeight)
{
TRACE_EVENT0("gpu.angle", "SwapChain11::resize");
ID3D11Device *device = mRenderer->getDevice();
- if (device == NULL)
+ if (device == nullptr)
{
return EGL_BAD_ACCESS;
}
@@ -427,18 +464,19 @@ EGLint SwapChain11::resize(EGLint backbufferWidth, EGLint backbufferHeight)
}
// Can only call resize if we have already created our swap buffer and resources
- ASSERT(mSwapChain && mBackBufferTexture && mBackBufferRTView && mBackBufferSRView);
+ ASSERT(mSwapChain && mBackBufferTexture.valid() && mBackBufferRTView.valid() &&
+ mBackBufferSRView.valid());
- SafeRelease(mBackBufferTexture);
- SafeRelease(mBackBufferRTView);
- SafeRelease(mBackBufferSRView);
+ mBackBufferTexture.reset();
+ mBackBufferRTView.reset();
+ mBackBufferSRView.reset();
// Resize swap chain
DXGI_SWAP_CHAIN_DESC desc;
HRESULT result = mSwapChain->GetDesc(&desc);
if (FAILED(result))
{
- ERR("Error reading swap chain description: 0x%08X", result);
+ ERR() << "Error reading swap chain description, " << gl::FmtHR(result);
release();
return EGL_BAD_ALLOC;
}
@@ -447,7 +485,7 @@ EGLint SwapChain11::resize(EGLint backbufferWidth, EGLint backbufferHeight)
if (FAILED(result))
{
- ERR("Error resizing swap chain buffers: 0x%08X", result);
+ ERR() << "Error resizing swap chain buffers, " << gl::FmtHR(result);
release();
if (d3d11::isDeviceLostError(result))
@@ -460,39 +498,64 @@ EGLint SwapChain11::resize(EGLint backbufferWidth, EGLint backbufferHeight)
}
}
- result = mSwapChain->GetBuffer(0, __uuidof(ID3D11Texture2D), (LPVOID*)&mBackBufferTexture);
+ ID3D11Texture2D *backbufferTexture = nullptr;
+ result = mSwapChain->GetBuffer(0, __uuidof(ID3D11Texture2D),
+ reinterpret_cast<void **>(&backbufferTexture));
ASSERT(SUCCEEDED(result));
if (SUCCEEDED(result))
{
- d3d11::SetDebugName(mBackBufferTexture, "Back buffer texture");
- result = device->CreateRenderTargetView(mBackBufferTexture, NULL, &mBackBufferRTView);
- ASSERT(SUCCEEDED(result));
- if (SUCCEEDED(result))
- {
- d3d11::SetDebugName(mBackBufferRTView, "Back buffer render target");
- }
-
- result = device->CreateShaderResourceView(mBackBufferTexture, nullptr, &mBackBufferSRView);
- ASSERT(SUCCEEDED(result));
- if (SUCCEEDED(result))
- {
- d3d11::SetDebugName(mBackBufferSRView, "Back buffer shader resource");
- }
+ const auto &format =
+ d3d11::Format::Get(mOffscreenRenderTargetFormat, mRenderer->getRenderer11DeviceCaps());
+ mBackBufferTexture.set(backbufferTexture, format);
+ mBackBufferTexture.setDebugName("Back buffer texture");
+
+ gl::Error err =
+ mRenderer->allocateResourceNoDesc(mBackBufferTexture.get(), &mBackBufferRTView);
+ ASSERT(!err.isError());
+ mBackBufferRTView.setDebugName("Back buffer render target");
+
+ err = mRenderer->allocateResourceNoDesc(mBackBufferTexture.get(), &mBackBufferSRView);
+ ASSERT(!err.isError());
+ mBackBufferSRView.setDebugName("Back buffer shader resource");
}
mFirstSwap = true;
- return resetOffscreenBuffers(backbufferWidth, backbufferHeight);
+ return resetOffscreenBuffers(context, backbufferWidth, backbufferHeight);
}
DXGI_FORMAT SwapChain11::getSwapChainNativeFormat() const
{
// Return a render target format for offscreen rendering is supported by IDXGISwapChain.
// MSDN https://msdn.microsoft.com/en-us/library/windows/desktop/bb173064(v=vs.85).aspx
- return (mOffscreenRenderTargetFormat == GL_BGRA8_EXT) ? DXGI_FORMAT_B8G8R8A8_UNORM : DXGI_FORMAT_R8G8B8A8_UNORM;
+ switch (mOffscreenRenderTargetFormat)
+ {
+ case GL_RGBA8:
+ case GL_RGBA4:
+ case GL_RGB5_A1:
+ case GL_RGB8:
+ case GL_RGB565:
+ return DXGI_FORMAT_R8G8B8A8_UNORM;
+
+ case GL_BGRA8_EXT:
+ return DXGI_FORMAT_B8G8R8A8_UNORM;
+
+ case GL_RGB10_A2:
+ return DXGI_FORMAT_R10G10B10A2_UNORM;
+
+ case GL_RGBA16F:
+ return DXGI_FORMAT_R16G16B16A16_FLOAT;
+
+ default:
+ UNREACHABLE();
+ return DXGI_FORMAT_UNKNOWN;
+ }
}
-EGLint SwapChain11::reset(int backbufferWidth, int backbufferHeight, EGLint swapInterval)
+EGLint SwapChain11::reset(const gl::Context *context,
+ EGLint backbufferWidth,
+ EGLint backbufferHeight,
+ EGLint swapInterval)
{
mSwapInterval = static_cast<unsigned int>(swapInterval);
if (mSwapInterval > 4)
@@ -505,25 +568,23 @@ EGLint SwapChain11::reset(int backbufferWidth, int backbufferHeight, EGLint swap
// If the swap chain already exists, just resize
if (mSwapChain != nullptr)
{
- return resize(backbufferWidth, backbufferHeight);
+ return resize(context, backbufferWidth, backbufferHeight);
}
TRACE_EVENT0("gpu.angle", "SwapChain11::reset");
ID3D11Device *device = mRenderer->getDevice();
- if (device == NULL)
+ if (device == nullptr)
{
return EGL_BAD_ACCESS;
}
// Release specific resources to free up memory for the new render target, while the
// old render target still exists for the purpose of preserving its contents.
-#if defined(ANGLE_ENABLE_D3D11_1)
SafeRelease(mSwapChain1);
-#endif
SafeRelease(mSwapChain);
- SafeRelease(mBackBufferTexture);
- SafeRelease(mBackBufferRTView);
+ mBackBufferTexture.reset();
+ mBackBufferRTView.reset();
// EGL allows creating a surface with 0x0 dimension, however, DXGI does not like 0x0 swapchains
if (backbufferWidth < 1 || backbufferHeight < 1)
@@ -532,15 +593,16 @@ EGLint SwapChain11::reset(int backbufferWidth, int backbufferHeight, EGLint swap
return EGL_SUCCESS;
}
- if (mNativeWindow.getNativeWindow())
+ if (mNativeWindow->getNativeWindow())
{
- HRESULT result = mNativeWindow.createSwapChain(device, mRenderer->getDxgiFactory(),
- getSwapChainNativeFormat(),
- backbufferWidth, backbufferHeight, &mSwapChain);
+ HRESULT result = mNativeWindow->createSwapChain(
+ device, mRenderer->getDxgiFactory(), getSwapChainNativeFormat(), backbufferWidth,
+ backbufferHeight, getD3DSamples(), &mSwapChain);
if (FAILED(result))
{
- ERR("Could not create additional swap chains or offscreen surfaces: %08lX", result);
+ ERR() << "Could not create additional swap chains or offscreen surfaces, "
+ << gl::FmtHR(result);
release();
if (d3d11::isDeviceLostError(result))
@@ -555,27 +617,31 @@ EGLint SwapChain11::reset(int backbufferWidth, int backbufferHeight, EGLint swap
if (mRenderer->getRenderer11DeviceCaps().supportsDXGI1_2)
{
-#if defined(ANGLE_ENABLE_D3D11_1)
mSwapChain1 = d3d11::DynamicCastComObject<IDXGISwapChain1>(mSwapChain);
-#endif
}
- result = mSwapChain->GetBuffer(0, __uuidof(ID3D11Texture2D), (LPVOID*)&mBackBufferTexture);
- ASSERT(SUCCEEDED(result));
- d3d11::SetDebugName(mBackBufferTexture, "Back buffer texture");
-
- result = device->CreateRenderTargetView(mBackBufferTexture, NULL, &mBackBufferRTView);
- ASSERT(SUCCEEDED(result));
- d3d11::SetDebugName(mBackBufferRTView, "Back buffer render target");
-
- result = device->CreateShaderResourceView(mBackBufferTexture, nullptr, &mBackBufferSRView);
+ ID3D11Texture2D *backbufferTex = nullptr;
+ result = mSwapChain->GetBuffer(0, __uuidof(ID3D11Texture2D),
+ reinterpret_cast<LPVOID *>(&backbufferTex));
ASSERT(SUCCEEDED(result));
- d3d11::SetDebugName(mBackBufferSRView, "Back buffer shader resource view");
+ const auto &format =
+ d3d11::Format::Get(mOffscreenRenderTargetFormat, mRenderer->getRenderer11DeviceCaps());
+ mBackBufferTexture.set(backbufferTex, format);
+ mBackBufferTexture.setDebugName("Back buffer texture");
+
+ gl::Error err =
+ mRenderer->allocateResourceNoDesc(mBackBufferTexture.get(), &mBackBufferRTView);
+ ASSERT(!err.isError());
+ mBackBufferRTView.setDebugName("Back buffer render target");
+
+ err = mRenderer->allocateResourceNoDesc(mBackBufferTexture.get(), &mBackBufferSRView);
+ ASSERT(!err.isError());
+ mBackBufferSRView.setDebugName("Back buffer shader resource view");
}
mFirstSwap = true;
- return resetOffscreenBuffers(backbufferWidth, backbufferHeight);
+ return resetOffscreenBuffers(context, backbufferWidth, backbufferHeight);
}
void SwapChain11::initPassThroughResources()
@@ -588,11 +654,11 @@ void SwapChain11::initPassThroughResources()
TRACE_EVENT0("gpu.angle", "SwapChain11::initPassThroughResources");
ID3D11Device *device = mRenderer->getDevice();
- ASSERT(device != NULL);
+ ASSERT(device != nullptr);
// Make sure our resources are all not allocated, when we create
- ASSERT(mQuadVB == NULL && mPassThroughSampler == NULL);
- ASSERT(mPassThroughIL == NULL && mPassThroughVS == NULL && mPassThroughPS == NULL);
+ ASSERT(!mQuadVB.valid() && !mPassThroughSampler.valid());
+ ASSERT(!mPassThroughIL.valid() && !mPassThroughVS.valid() && !mPassThroughPS.valid());
D3D11_BUFFER_DESC vbDesc;
vbDesc.ByteWidth = sizeof(d3d11::PositionTexCoordVertex) * 4;
@@ -602,9 +668,9 @@ void SwapChain11::initPassThroughResources()
vbDesc.MiscFlags = 0;
vbDesc.StructureByteStride = 0;
- HRESULT result = device->CreateBuffer(&vbDesc, NULL, &mQuadVB);
- ASSERT(SUCCEEDED(result));
- d3d11::SetDebugName(mQuadVB, "Swap chain quad vertex buffer");
+ gl::Error err = mRenderer->allocateResource(vbDesc, &mQuadVB);
+ ASSERT(!err.isError());
+ mQuadVB.setDebugName("Swap chain quad vertex buffer");
D3D11_SAMPLER_DESC samplerDesc;
samplerDesc.Filter = D3D11_FILTER_MIN_MAG_MIP_POINT;
@@ -621,9 +687,9 @@ void SwapChain11::initPassThroughResources()
samplerDesc.MinLOD = 0;
samplerDesc.MaxLOD = D3D11_FLOAT32_MAX;
- result = device->CreateSamplerState(&samplerDesc, &mPassThroughSampler);
- ASSERT(SUCCEEDED(result));
- d3d11::SetDebugName(mPassThroughSampler, "Swap chain pass through sampler");
+ err = mRenderer->allocateResource(samplerDesc, &mPassThroughSampler);
+ ASSERT(!err.isError());
+ mPassThroughSampler.setDebugName("Swap chain pass through sampler");
D3D11_INPUT_ELEMENT_DESC quadLayout[] =
{
@@ -631,17 +697,30 @@ void SwapChain11::initPassThroughResources()
{ "TEXCOORD", 0, DXGI_FORMAT_R32G32_FLOAT, 0, 8, D3D11_INPUT_PER_VERTEX_DATA, 0 },
};
- result = device->CreateInputLayout(quadLayout, 2, g_VS_Passthrough2D, sizeof(g_VS_Passthrough2D), &mPassThroughIL);
- ASSERT(SUCCEEDED(result));
- d3d11::SetDebugName(mPassThroughIL, "Swap chain pass through layout");
+ InputElementArray quadElements(quadLayout);
+ ShaderData vertexShaderData(g_VS_Passthrough2D);
- result = device->CreateVertexShader(g_VS_Passthrough2D, sizeof(g_VS_Passthrough2D), NULL, &mPassThroughVS);
- ASSERT(SUCCEEDED(result));
- d3d11::SetDebugName(mPassThroughVS, "Swap chain pass through vertex shader");
+ err = mRenderer->allocateResource(quadElements, &vertexShaderData, &mPassThroughIL);
+ ASSERT(!err.isError());
+ mPassThroughIL.setDebugName("Swap chain pass through layout");
- result = device->CreatePixelShader(g_PS_PassthroughRGBA2D, sizeof(g_PS_PassthroughRGBA2D), NULL, &mPassThroughPS);
- ASSERT(SUCCEEDED(result));
- d3d11::SetDebugName(mPassThroughPS, "Swap chain pass through pixel shader");
+ err = mRenderer->allocateResource(vertexShaderData, &mPassThroughVS);
+ ASSERT(!err.isError());
+ mPassThroughVS.setDebugName("Swap chain pass through vertex shader");
+
+ if (mEGLSamples <= 1)
+ {
+ ShaderData pixelShaderData(g_PS_PassthroughRGBA2D);
+ err = mRenderer->allocateResource(pixelShaderData, &mPassThroughPS);
+ }
+ else
+ {
+ ShaderData pixelShaderData(g_PS_PassthroughRGBA2DMS);
+ err = mRenderer->allocateResource(pixelShaderData, &mPassThroughPS);
+ }
+
+ ASSERT(!err.isError());
+ mPassThroughPS.setDebugName("Swap chain pass through pixel shader");
// Use the default rasterizer state but without culling
D3D11_RASTERIZER_DESC rasterizerDesc;
@@ -655,26 +734,31 @@ void SwapChain11::initPassThroughResources()
rasterizerDesc.ScissorEnable = FALSE;
rasterizerDesc.MultisampleEnable = FALSE;
rasterizerDesc.AntialiasedLineEnable = FALSE;
- result = device->CreateRasterizerState(&rasterizerDesc, &mPassThroughRS);
- ASSERT(SUCCEEDED(result));
- d3d11::SetDebugName(mPassThroughRS, "Swap chain pass through rasterizer state");
+
+ err = mRenderer->allocateResource(rasterizerDesc, &mPassThroughRS);
+ ASSERT(!err.isError());
+ mPassThroughRS.setDebugName("Swap chain pass through rasterizer state");
mPassThroughResourcesInit = true;
}
// parameters should be validated/clamped by caller
-EGLint SwapChain11::swapRect(EGLint x, EGLint y, EGLint width, EGLint height)
+EGLint SwapChain11::swapRect(const gl::Context *context,
+ EGLint x,
+ EGLint y,
+ EGLint width,
+ EGLint height)
{
if (mNeedsOffscreenTexture)
{
- EGLint result = copyOffscreenToBackbuffer(x, y, width, height);
+ EGLint result = copyOffscreenToBackbuffer(context, x, y, width, height);
if (result != EGL_SUCCESS)
{
return result;
}
}
- EGLint result = present(x, y, width, height);
+ EGLint result = present(context, x, y, width, height);
if (result != EGL_SUCCESS)
{
return result;
@@ -685,7 +769,11 @@ EGLint SwapChain11::swapRect(EGLint x, EGLint y, EGLint width, EGLint height)
return EGL_SUCCESS;
}
-EGLint SwapChain11::copyOffscreenToBackbuffer(EGLint x, EGLint y, EGLint width, EGLint height)
+EGLint SwapChain11::copyOffscreenToBackbuffer(const gl::Context *context,
+ EGLint x,
+ EGLint y,
+ EGLint width,
+ EGLint height)
{
if (!mSwapChain)
{
@@ -698,7 +786,8 @@ EGLint SwapChain11::copyOffscreenToBackbuffer(EGLint x, EGLint y, EGLint width,
// Set vertices
D3D11_MAPPED_SUBRESOURCE mappedResource;
- HRESULT result = deviceContext->Map(mQuadVB, 0, D3D11_MAP_WRITE_DISCARD, 0, &mappedResource);
+ HRESULT result =
+ deviceContext->Map(mQuadVB.get(), 0, D3D11_MAP_WRITE_DISCARD, 0, &mappedResource);
if (FAILED(result))
{
return EGL_BAD_ACCESS;
@@ -716,7 +805,6 @@ EGLint SwapChain11::copyOffscreenToBackbuffer(EGLint x, EGLint y, EGLint width,
float v1 = y / float(height);
float u2 = (x + width) / float(width);
float v2 = (y + height) / float(height);
-
// Invert the quad vertices depending on the surface orientation.
if ((mOrientation & EGL_SURFACE_ORIENTATION_INVERT_X_ANGLE) != 0)
{
@@ -732,60 +820,43 @@ EGLint SwapChain11::copyOffscreenToBackbuffer(EGLint x, EGLint y, EGLint width,
d3d11::SetPositionTexCoordVertex(&vertices[2], x2, y1, u2, v1);
d3d11::SetPositionTexCoordVertex(&vertices[3], x2, y2, u2, v2);
- deviceContext->Unmap(mQuadVB, 0);
+ deviceContext->Unmap(mQuadVB.get(), 0);
- static UINT stride = sizeof(d3d11::PositionTexCoordVertex);
- static UINT startIdx = 0;
- deviceContext->IASetVertexBuffers(0, 1, &mQuadVB, &stride, &startIdx);
-
- // Apply state
- deviceContext->OMSetDepthStencilState(NULL, 0xFFFFFFFF);
+ StateManager11 *stateManager = mRenderer->getStateManager();
- static const float blendFactor[4] = { 1.0f, 1.0f, 1.0f, 1.0f };
- deviceContext->OMSetBlendState(NULL, blendFactor, 0xFFFFFFF);
+ constexpr UINT stride = sizeof(d3d11::PositionTexCoordVertex);
+ stateManager->setSingleVertexBuffer(&mQuadVB, stride, 0);
- deviceContext->RSSetState(mPassThroughRS);
+ // Apply state
+ stateManager->setDepthStencilState(nullptr, 0xFFFFFFFF);
+ stateManager->setSimpleBlendState(nullptr);
+ stateManager->setRasterizerState(&mPassThroughRS);
// Apply shaders
- deviceContext->IASetInputLayout(mPassThroughIL);
- deviceContext->IASetPrimitiveTopology(D3D_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP);
- deviceContext->VSSetShader(mPassThroughVS, NULL, 0);
- deviceContext->PSSetShader(mPassThroughPS, NULL, 0);
- deviceContext->GSSetShader(NULL, NULL, 0);
+ stateManager->setInputLayout(&mPassThroughIL);
+ stateManager->setPrimitiveTopology(D3D_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP);
+ stateManager->setDrawShaders(&mPassThroughVS, nullptr, &mPassThroughPS);
- // Apply render targets
- mRenderer->setOneTimeRenderTarget(mBackBufferRTView);
+ // Apply render targets. Use the proxy context in display.
+ stateManager->setRenderTarget(mBackBufferRTView.get(), nullptr);
// Set the viewport
- D3D11_VIEWPORT viewport;
- viewport.TopLeftX = 0;
- viewport.TopLeftY = 0;
- viewport.Width = static_cast<FLOAT>(width);
- viewport.Height = static_cast<FLOAT>(height);
- viewport.MinDepth = 0.0f;
- viewport.MaxDepth = 1.0f;
- deviceContext->RSSetViewports(1, &viewport);
+ stateManager->setSimpleViewport(mWidth, mHeight);
// Apply textures
- auto stateManager = mRenderer->getStateManager();
- stateManager->setShaderResource(gl::SAMPLER_PIXEL, 0, mOffscreenSRView);
- deviceContext->PSSetSamplers(0, 1, &mPassThroughSampler);
+ stateManager->setSimplePixelTextureAndSampler(mOffscreenSRView, mPassThroughSampler);
// Draw
deviceContext->Draw(4, 0);
- // Rendering to the swapchain is now complete. Now we can call Present().
- // Before that, we perform any cleanup on the D3D device. We do this before Present() to make sure the
- // cleanup is caught under the current eglSwapBuffers() PIX/Graphics Diagnostics call rather than the next one.
- stateManager->setShaderResource(gl::SAMPLER_PIXEL, 0, NULL);
-
- mRenderer->unapplyRenderTargets();
- mRenderer->markAllStateDirty();
-
return EGL_SUCCESS;
}
-EGLint SwapChain11::present(EGLint x, EGLint y, EGLint width, EGLint height)
+EGLint SwapChain11::present(const gl::Context *context,
+ EGLint x,
+ EGLint y,
+ EGLint width,
+ EGLint height)
{
if (!mSwapChain)
{
@@ -799,9 +870,9 @@ EGLint SwapChain11::present(EGLint x, EGLint y, EGLint width, EGLint height)
HRESULT result = S_OK;
-#if defined(ANGLE_ENABLE_D3D11_1)
// Use IDXGISwapChain1::Present1 with a dirty rect if DXGI 1.2 is available.
- if (mSwapChain1 != nullptr)
+ // Dirty rect present is not supported with a multisampled swapchain.
+ if (mSwapChain1 != nullptr && mEGLSamples <= 1)
{
if (mFirstSwap)
{
@@ -818,7 +889,6 @@ EGLint SwapChain11::present(EGLint x, EGLint y, EGLint width, EGLint height)
}
}
else
-#endif
{
result = mSwapChain->Present(swapInterval, 0);
}
@@ -826,60 +896,111 @@ EGLint SwapChain11::present(EGLint x, EGLint y, EGLint width, EGLint height)
mFirstSwap = false;
// Some swapping mechanisms such as DXGI_SWAP_EFFECT_FLIP_SEQUENTIAL unbind the current render
- // target. Mark it dirty.
+ // target. Mark it dirty. Use the proxy context in display since there is none available.
mRenderer->getStateManager()->invalidateRenderTarget();
if (result == DXGI_ERROR_DEVICE_REMOVED)
{
- ERR("Present failed: the D3D11 device was removed: 0x%08X",
- mRenderer->getDevice()->GetDeviceRemovedReason());
+ ERR() << "Present failed: the D3D11 device was removed, "
+ << gl::FmtHR(mRenderer->getDevice()->GetDeviceRemovedReason());
return EGL_CONTEXT_LOST;
}
else if (result == DXGI_ERROR_DEVICE_RESET)
{
- ERR("Present failed: the D3D11 device was reset from a bad command.");
+ ERR() << "Present failed: the D3D11 device was reset from a bad command.";
return EGL_CONTEXT_LOST;
}
else if (FAILED(result))
{
- ERR("Present failed with error code 0x%08X", result);
+ ERR() << "Present failed with " << gl::FmtHR(result);
}
- mNativeWindow.commitChange();
+ mNativeWindow->commitChange();
return EGL_SUCCESS;
}
-ID3D11Texture2D *SwapChain11::getOffscreenTexture()
+const TextureHelper11 &SwapChain11::getOffscreenTexture()
{
return mNeedsOffscreenTexture ? mOffscreenTexture : mBackBufferTexture;
}
-ID3D11RenderTargetView *SwapChain11::getRenderTarget()
+const d3d11::RenderTargetView &SwapChain11::getRenderTarget()
{
return mNeedsOffscreenTexture ? mOffscreenRTView : mBackBufferRTView;
}
-ID3D11ShaderResourceView *SwapChain11::getRenderTargetShaderResource()
+const d3d11::SharedSRV &SwapChain11::getRenderTargetShaderResource()
{
- return mNeedsOffscreenTexture ? mOffscreenSRView : mBackBufferSRView;
+ if (!mNeedsOffscreenTexture)
+ {
+ ASSERT(mBackBufferSRView.valid());
+ return mBackBufferSRView;
+ }
+
+ if (!mNeedsOffscreenTextureCopy)
+ {
+ ASSERT(mOffscreenSRView.valid());
+ return mOffscreenSRView;
+ }
+
+ if (!mOffscreenTextureCopyForSRV.valid())
+ {
+ const d3d11::Format &backbufferFormatInfo =
+ d3d11::Format::Get(mOffscreenRenderTargetFormat, mRenderer->getRenderer11DeviceCaps());
+
+ D3D11_TEXTURE2D_DESC offscreenCopyDesc;
+ mOffscreenTexture.getDesc(&offscreenCopyDesc);
+
+ offscreenCopyDesc.BindFlags = D3D11_BIND_SHADER_RESOURCE;
+ offscreenCopyDesc.MiscFlags = 0;
+ offscreenCopyDesc.CPUAccessFlags = 0;
+ gl::Error err = mRenderer->allocateTexture(offscreenCopyDesc, backbufferFormatInfo,
+ &mOffscreenTextureCopyForSRV);
+ ASSERT(!err.isError());
+ mOffscreenTextureCopyForSRV.setDebugName("Offscreen back buffer copy for SRV");
+
+ D3D11_SHADER_RESOURCE_VIEW_DESC offscreenSRVDesc;
+ offscreenSRVDesc.Format = backbufferFormatInfo.srvFormat;
+ offscreenSRVDesc.ViewDimension =
+ (mEGLSamples <= 1) ? D3D11_SRV_DIMENSION_TEXTURE2D : D3D11_SRV_DIMENSION_TEXTURE2DMS;
+ offscreenSRVDesc.Texture2D.MostDetailedMip = 0;
+ offscreenSRVDesc.Texture2D.MipLevels = static_cast<UINT>(-1);
+
+ err = mRenderer->allocateResource(offscreenSRVDesc, mOffscreenTextureCopyForSRV.get(),
+ &mOffscreenSRView);
+ ASSERT(!err.isError());
+ mOffscreenSRView.setDebugName("Offscreen back buffer shader resource");
+ }
+
+ // Need to copy the offscreen texture into the shader-readable copy, since it's external and
+ // we don't know if the copy is up-to-date. This works around the problem we have when the app
+ // passes in a texture that isn't shader-readable.
+ mRenderer->getDeviceContext()->CopyResource(mOffscreenTextureCopyForSRV.get(),
+ mOffscreenTexture.get());
+ return mOffscreenSRView;
}
-ID3D11DepthStencilView *SwapChain11::getDepthStencil()
+const d3d11::DepthStencilView &SwapChain11::getDepthStencil()
{
return mDepthStencilDSView;
}
-ID3D11ShaderResourceView * SwapChain11::getDepthStencilShaderResource()
+const d3d11::SharedSRV &SwapChain11::getDepthStencilShaderResource()
{
return mDepthStencilSRView;
}
-ID3D11Texture2D *SwapChain11::getDepthStencilTexture()
+const TextureHelper11 &SwapChain11::getDepthStencilTexture()
{
return mDepthStencilTexture;
}
+void *SwapChain11::getKeyedMutex()
+{
+ return mKeyedMutex;
+}
+
void SwapChain11::recreate()
{
// possibly should use this method instead of reset
@@ -890,4 +1011,61 @@ void *rx::SwapChain11::getDevice()
return mRenderer->getDevice();
}
+RenderTargetD3D *SwapChain11::getColorRenderTarget()
+{
+ return &mColorRenderTarget;
+}
+
+RenderTargetD3D *SwapChain11::getDepthStencilRenderTarget()
+{
+ return &mDepthStencilRenderTarget;
+}
+
+egl::Error SwapChain11::getSyncValues(EGLuint64KHR *ust, EGLuint64KHR *msc, EGLuint64KHR *sbc)
+{
+ if (!mSwapChain)
+ {
+ return egl::EglNotInitialized() << "Swap chain uninitialized";
+ }
+
+ DXGI_FRAME_STATISTICS stats = {};
+ HRESULT result = mSwapChain->GetFrameStatistics(&stats);
+
+ if (FAILED(result))
+ {
+ return egl::EglBadAlloc() << "Failed to get frame statistics, " << gl::FmtHR(result);
+ }
+
+ // Conversion from DXGI_FRAME_STATISTICS to the output values:
+ // stats.SyncRefreshCount -> msc
+ // stats.PresentCount -> sbc
+ // stats.SyncQPCTime -> ust with conversion to microseconds via QueryPerformanceFrequency
+ *msc = stats.SyncRefreshCount;
+ *sbc = stats.PresentCount;
+
+ LONGLONG syncQPCValue = stats.SyncQPCTime.QuadPart;
+ // If the QPC Value is below the overflow threshold, we proceed with
+ // simple multiply and divide.
+ if (syncQPCValue < kQPCOverflowThreshold)
+ {
+ *ust = syncQPCValue * kMicrosecondsPerSecond / mQPCFrequency;
+ }
+ else
+ {
+ // Otherwise, calculate microseconds in a round about manner to avoid
+ // overflow and precision issues.
+ int64_t wholeSeconds = syncQPCValue / mQPCFrequency;
+ int64_t leftoverTicks = syncQPCValue - (wholeSeconds * mQPCFrequency);
+ *ust = wholeSeconds * kMicrosecondsPerSecond +
+ leftoverTicks * kMicrosecondsPerSecond / mQPCFrequency;
+ }
+
+ return egl::NoError();
+}
+
+UINT SwapChain11::getD3DSamples() const
+{
+ return (mEGLSamples == 0) ? 1 : mEGLSamples;
}
+
+} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/SwapChain11.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/SwapChain11.h
index adcd07adb0..eca068210b 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/SwapChain11.h
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/SwapChain11.h
@@ -16,39 +16,54 @@
namespace rx
{
class Renderer11;
+class NativeWindow11;
-class SwapChain11 : public SwapChainD3D
+class SwapChain11 final : public SwapChainD3D
{
public:
SwapChain11(Renderer11 *renderer,
- NativeWindow nativeWindow,
+ NativeWindow11 *nativeWindow,
HANDLE shareHandle,
+ IUnknown *d3dTexture,
GLenum backBufferFormat,
GLenum depthBufferFormat,
- EGLint orientation);
- virtual ~SwapChain11();
-
- EGLint resize(EGLint backbufferWidth, EGLint backbufferHeight);
- virtual EGLint reset(EGLint backbufferWidth, EGLint backbufferHeight, EGLint swapInterval);
- virtual EGLint swapRect(EGLint x, EGLint y, EGLint width, EGLint height);
- virtual void recreate();
-
- RenderTargetD3D *getColorRenderTarget() override { return &mColorRenderTarget; }
- RenderTargetD3D *getDepthStencilRenderTarget() override { return &mDepthStencilRenderTarget; }
-
- virtual ID3D11Texture2D *getOffscreenTexture();
- virtual ID3D11RenderTargetView *getRenderTarget();
- virtual ID3D11ShaderResourceView *getRenderTargetShaderResource();
-
- virtual ID3D11Texture2D *getDepthStencilTexture();
- virtual ID3D11DepthStencilView *getDepthStencil();
- virtual ID3D11ShaderResourceView *getDepthStencilShaderResource();
+ EGLint orientation,
+ EGLint samples);
+ ~SwapChain11() override;
+
+ EGLint resize(const gl::Context *context,
+ EGLint backbufferWidth,
+ EGLint backbufferHeight) override;
+ EGLint reset(const gl::Context *context,
+ EGLint backbufferWidth,
+ EGLint backbufferHeight,
+ EGLint swapInterval) override;
+ EGLint swapRect(const gl::Context *context,
+ EGLint x,
+ EGLint y,
+ EGLint width,
+ EGLint height) override;
+ void recreate() override;
+
+ RenderTargetD3D *getColorRenderTarget() override;
+ RenderTargetD3D *getDepthStencilRenderTarget() override;
+
+ const TextureHelper11 &getOffscreenTexture();
+ const d3d11::RenderTargetView &getRenderTarget();
+ const d3d11::SharedSRV &getRenderTargetShaderResource();
+
+ const TextureHelper11 &getDepthStencilTexture();
+ const d3d11::DepthStencilView &getDepthStencil();
+ const d3d11::SharedSRV &getDepthStencilShaderResource();
EGLint getWidth() const { return mWidth; }
EGLint getHeight() const { return mHeight; }
- void *getKeyedMutex() override { return mKeyedMutex; }
+ void *getKeyedMutex() override;
+ EGLint getSamples() const { return mEGLSamples; }
+
+ void *getDevice() override;
- virtual void *getDevice();
+ egl::Error getSyncValues(EGLuint64KHR *ust, EGLuint64KHR *msc, EGLuint64KHR *sbc) override;
private:
void release();
@@ -56,14 +71,23 @@ class SwapChain11 : public SwapChainD3D
void releaseOffscreenColorBuffer();
void releaseOffscreenDepthBuffer();
- EGLint resetOffscreenBuffers(int backbufferWidth, int backbufferHeight);
- EGLint resetOffscreenColorBuffer(int backbufferWidth, int backbufferHeight);
+ EGLint resetOffscreenBuffers(const gl::Context *context,
+ int backbufferWidth,
+ int backbufferHeight);
+ EGLint resetOffscreenColorBuffer(const gl::Context *context,
+ int backbufferWidth,
+ int backbufferHeight);
EGLint resetOffscreenDepthBuffer(int backbufferWidth, int backbufferHeight);
DXGI_FORMAT getSwapChainNativeFormat() const;
- EGLint copyOffscreenToBackbuffer(EGLint x, EGLint y, EGLint width, EGLint height);
- EGLint present(EGLint x, EGLint y, EGLint width, EGLint height);
+ EGLint copyOffscreenToBackbuffer(const gl::Context *context,
+ EGLint x,
+ EGLint y,
+ EGLint width,
+ EGLint height);
+ EGLint present(const gl::Context *context, EGLint x, EGLint y, EGLint width, EGLint height);
+ UINT getD3DSamples() const;
Renderer11 *mRenderer;
EGLint mWidth;
@@ -73,36 +97,41 @@ class SwapChain11 : public SwapChainD3D
unsigned int mSwapInterval;
bool mPassThroughResourcesInit;
+ NativeWindow11 *mNativeWindow; // Handler for the Window that the surface is created for.
+
bool mFirstSwap;
- DXGISwapChain *mSwapChain;
-#if defined(ANGLE_ENABLE_D3D11_1)
+ IDXGISwapChain *mSwapChain;
IDXGISwapChain1 *mSwapChain1;
-#endif
IDXGIKeyedMutex *mKeyedMutex;
- ID3D11Texture2D *mBackBufferTexture;
- ID3D11RenderTargetView *mBackBufferRTView;
- ID3D11ShaderResourceView *mBackBufferSRView;
+ TextureHelper11 mBackBufferTexture;
+ d3d11::RenderTargetView mBackBufferRTView;
+ d3d11::SharedSRV mBackBufferSRView;
const bool mNeedsOffscreenTexture;
- ID3D11Texture2D *mOffscreenTexture;
- ID3D11RenderTargetView *mOffscreenRTView;
- ID3D11ShaderResourceView *mOffscreenSRView;
-
- ID3D11Texture2D *mDepthStencilTexture;
- ID3D11DepthStencilView *mDepthStencilDSView;
- ID3D11ShaderResourceView *mDepthStencilSRView;
-
- ID3D11Buffer *mQuadVB;
- ID3D11SamplerState *mPassThroughSampler;
- ID3D11InputLayout *mPassThroughIL;
- ID3D11VertexShader *mPassThroughVS;
- ID3D11PixelShader *mPassThroughPS;
- ID3D11RasterizerState *mPassThroughRS;
+ TextureHelper11 mOffscreenTexture;
+ d3d11::RenderTargetView mOffscreenRTView;
+ d3d11::SharedSRV mOffscreenSRView;
+ bool mNeedsOffscreenTextureCopy;
+ TextureHelper11 mOffscreenTextureCopyForSRV;
+
+ TextureHelper11 mDepthStencilTexture;
+ d3d11::DepthStencilView mDepthStencilDSView;
+ d3d11::SharedSRV mDepthStencilSRView;
+
+ d3d11::Buffer mQuadVB;
+ d3d11::SamplerState mPassThroughSampler;
+ d3d11::InputLayout mPassThroughIL;
+ d3d11::VertexShader mPassThroughVS;
+ d3d11::PixelShader mPassThroughPS;
+ d3d11::RasterizerState mPassThroughRS;
SurfaceRenderTarget11 mColorRenderTarget;
SurfaceRenderTarget11 mDepthStencilRenderTarget;
+
+ EGLint mEGLSamples;
+ LONGLONG mQPCFrequency;
};
-}
+} // namespace rx
#endif // LIBANGLE_RENDERER_D3D_D3D11_SWAPCHAIN11_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/TextureStorage11.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/TextureStorage11.cpp
index 11b9f76464..b702450ded 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/TextureStorage11.cpp
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/TextureStorage11.cpp
@@ -5,7 +5,8 @@
//
// TextureStorage11.cpp: Implements the abstract rx::TextureStorage11 class and its concrete derived
-// classes TextureStorage11_2D and TextureStorage11_Cube, which act as the interface to the D3D11 texture.
+// classes TextureStorage11_2D and TextureStorage11_Cube, which act as the interface to the D3D11
+// texture.
#include "libANGLE/renderer/d3d/d3d11/TextureStorage11.h"
@@ -21,6 +22,7 @@
#include "libANGLE/renderer/d3d/d3d11/Renderer11.h"
#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
#include "libANGLE/renderer/d3d/d3d11/RenderTarget11.h"
+#include "libANGLE/renderer/d3d/d3d11/StreamProducerNV12.h"
#include "libANGLE/renderer/d3d/d3d11/SwapChain11.h"
#include "libANGLE/renderer/d3d/d3d11/texture_format_table.h"
#include "libANGLE/renderer/d3d/EGLImageD3D.h"
@@ -29,82 +31,79 @@
namespace rx
{
-TextureStorage11::SwizzleCacheValue::SwizzleCacheValue()
- : swizzleRed(GL_INVALID_INDEX),
- swizzleGreen(GL_INVALID_INDEX),
- swizzleBlue(GL_INVALID_INDEX),
- swizzleAlpha(GL_INVALID_INDEX)
+namespace
{
+
+void InvalidateRenderTarget(const gl::Context *context, RenderTarget11 *renderTarget)
+{
+ if (renderTarget)
+ {
+ renderTarget->signalDirty(context);
+ }
}
-TextureStorage11::SwizzleCacheValue::SwizzleCacheValue(GLenum red, GLenum green, GLenum blue, GLenum alpha)
- : swizzleRed(red), swizzleGreen(green), swizzleBlue(blue), swizzleAlpha(alpha)
+RenderTarget11 *GetRenderTarget(std::unique_ptr<RenderTarget11> *pointer)
{
+ return pointer->get();
}
-bool TextureStorage11::SwizzleCacheValue::operator==(const SwizzleCacheValue &other) const
+template <typename KeyT>
+RenderTarget11 *GetRenderTarget(std::pair<KeyT, std::unique_ptr<RenderTarget11>> *pair)
{
- return swizzleRed == other.swizzleRed &&
- swizzleGreen == other.swizzleGreen &&
- swizzleBlue == other.swizzleBlue &&
- swizzleAlpha == other.swizzleAlpha;
+ return pair->second.get();
}
-bool TextureStorage11::SwizzleCacheValue::operator!=(const SwizzleCacheValue &other) const
+template <typename T>
+void InvalidateRenderTargetContainer(const gl::Context *context, T *renderTargetContainer)
{
- return !(*this == other);
+ for (auto &rt : *renderTargetContainer)
+ {
+ InvalidateRenderTarget(context, GetRenderTarget(&rt));
+ }
}
-TextureStorage11::SRVKey::SRVKey(int baseLevel, int mipLevels, bool swizzle)
- : baseLevel(baseLevel), mipLevels(mipLevels), swizzle(swizzle)
+} // anonymous namespace
+
+TextureStorage11::SRVKey::SRVKey(int baseLevel, int mipLevels, bool swizzle, bool dropStencil)
+ : baseLevel(baseLevel), mipLevels(mipLevels), swizzle(swizzle), dropStencil(dropStencil)
{
}
bool TextureStorage11::SRVKey::operator<(const SRVKey &rhs) const
{
- return std::tie(baseLevel, mipLevels, swizzle) < std::tie(rhs.baseLevel, rhs.mipLevels, rhs.swizzle);
+ return std::tie(baseLevel, mipLevels, swizzle, dropStencil) <
+ std::tie(rhs.baseLevel, rhs.mipLevels, rhs.swizzle, rhs.dropStencil);
}
-TextureStorage11::TextureStorage11(Renderer11 *renderer, UINT bindFlags, UINT miscFlags)
+TextureStorage11::TextureStorage11(Renderer11 *renderer,
+ UINT bindFlags,
+ UINT miscFlags,
+ GLenum internalFormat)
: mRenderer(renderer),
mTopLevel(0),
mMipLevels(0),
- mInternalFormat(GL_NONE),
- mTextureFormat(DXGI_FORMAT_UNKNOWN),
- mShaderResourceFormat(DXGI_FORMAT_UNKNOWN),
- mRenderTargetFormat(DXGI_FORMAT_UNKNOWN),
- mDepthStencilFormat(DXGI_FORMAT_UNKNOWN),
+ mFormatInfo(d3d11::Format::Get(internalFormat, mRenderer->getRenderer11DeviceCaps())),
mTextureWidth(0),
mTextureHeight(0),
mTextureDepth(0),
+ mDropStencilTexture(),
mBindFlags(bindFlags),
mMiscFlags(miscFlags)
{
- for (unsigned int i = 0; i < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS; i++)
- {
- mLevelSRVs[i] = nullptr;
- }
}
TextureStorage11::~TextureStorage11()
{
- for (unsigned int level = 0; level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS; level++)
- {
- SafeRelease(mLevelSRVs[level]);
- }
-
- for (SRVCache::iterator i = mSrvCache.begin(); i != mSrvCache.end(); i++)
- {
- SafeRelease(i->second);
- }
mSrvCache.clear();
}
-DWORD TextureStorage11::GetTextureBindFlags(GLenum internalFormat, const Renderer11DeviceCaps &renderer11DeviceCaps, bool renderTarget)
+DWORD TextureStorage11::GetTextureBindFlags(GLenum internalFormat,
+ const Renderer11DeviceCaps &renderer11DeviceCaps,
+ bool renderTarget)
{
UINT bindFlags = 0;
- const d3d11::TextureFormat &formatInfo = d3d11::GetTextureFormatInfo(internalFormat, renderer11DeviceCaps);
+ const d3d11::Format &formatInfo = d3d11::Format::Get(internalFormat, renderer11DeviceCaps);
if (formatInfo.srvFormat != DXGI_FORMAT_UNKNOWN)
{
bindFlags |= D3D11_BIND_SHADER_RESOURCE;
@@ -121,16 +120,17 @@ DWORD TextureStorage11::GetTextureBindFlags(GLenum internalFormat, const Rendere
return bindFlags;
}
-DWORD TextureStorage11::GetTextureMiscFlags(GLenum internalFormat, const Renderer11DeviceCaps &renderer11DeviceCaps, bool renderTarget, int levels)
+DWORD TextureStorage11::GetTextureMiscFlags(GLenum internalFormat,
+ const Renderer11DeviceCaps &renderer11DeviceCaps,
+ bool renderTarget,
+ int levels)
{
UINT miscFlags = 0;
- const d3d11::TextureFormat &formatInfo = d3d11::GetTextureFormatInfo(internalFormat, renderer11DeviceCaps);
+ const d3d11::Format &formatInfo = d3d11::Format::Get(internalFormat, renderer11DeviceCaps);
if (renderTarget && levels > 1)
{
- const d3d11::DXGIFormat &dxgiFormatInfo = d3d11::GetDXGIFormatInfo(formatInfo.texFormat);
-
- if (dxgiFormatInfo.nativeMipmapSupport(renderer11DeviceCaps.featureLevel))
+ if (d3d11::SupportsMipGen(formatInfo.texFormat, renderer11DeviceCaps.featureLevel))
{
miscFlags |= D3D11_RESOURCE_MISC_GENERATE_MIPS;
}
@@ -151,6 +151,8 @@ UINT TextureStorage11::getMiscFlags() const
int TextureStorage11::getTopLevel() const
{
+ // Applying top level is meant to be encapsulated inside TextureStorage11.
+ UNREACHABLE();
return mTopLevel;
}
@@ -189,24 +191,35 @@ int TextureStorage11::getLevelDepth(int mipLevel) const
return std::max(static_cast<int>(mTextureDepth) >> mipLevel, 1);
}
+gl::Error TextureStorage11::getMippedResource(const gl::Context *context,
+ const TextureHelper11 **outResource)
+{
+ return getResource(context, outResource);
+}
+
UINT TextureStorage11::getSubresourceIndex(const gl::ImageIndex &index) const
{
- UINT mipSlice = static_cast<UINT>(index.mipIndex + mTopLevel);
- UINT arraySlice = static_cast<UINT>(index.hasLayer() ? index.layerIndex : 0);
+ UINT mipSlice = static_cast<UINT>(index.mipIndex + mTopLevel);
+ UINT arraySlice = static_cast<UINT>(index.hasLayer() ? index.layerIndex : 0);
UINT subresource = D3D11CalcSubresource(mipSlice, arraySlice, mMipLevels);
ASSERT(subresource != std::numeric_limits<UINT>::max());
return subresource;
}
-gl::Error TextureStorage11::getSRV(const gl::TextureState &textureState,
- ID3D11ShaderResourceView **outSRV)
+gl::Error TextureStorage11::getSRV(const gl::Context *context,
+ const gl::TextureState &textureState,
+ const d3d11::SharedSRV **outSRV)
{
- bool swizzleRequired = textureState.swizzleRequired();
- bool mipmapping = gl::IsMipmapFiltered(textureState.samplerState);
- unsigned int mipLevels = mipmapping ? (textureState.maxLevel - textureState.baseLevel + 1) : 1;
+ // Make sure to add the level offset for our tiny compressed texture workaround
+ const GLuint effectiveBaseLevel = textureState.getEffectiveBaseLevel();
+ bool swizzleRequired = textureState.swizzleRequired();
+ bool mipmapping = gl::IsMipmapFiltered(textureState.getSamplerState());
+ unsigned int mipLevels =
+ mipmapping ? (textureState.getEffectiveMaxLevel() - effectiveBaseLevel + 1) : 1;
- // Make sure there's 'mipLevels' mipmap levels below the base level (offset by the top level, which corresponds to GL level 0)
- mipLevels = std::min(mipLevels, mMipLevels - mTopLevel - textureState.baseLevel);
+ // Make sure there's 'mipLevels' mipmap levels below the base level (offset by the top level,
+ // which corresponds to GL level 0)
+ mipLevels = std::min(mipLevels, mMipLevels - mTopLevel - effectiveBaseLevel);
if (mRenderer->getRenderer11DeviceCaps().featureLevel <= D3D_FEATURE_LEVEL_9_3)
{
@@ -217,89 +230,133 @@ gl::Error TextureStorage11::getSRV(const gl::TextureState &textureState,
if (mRenderer->getWorkarounds().zeroMaxLodWorkaround)
{
// We must ensure that the level zero texture is in sync with mipped texture.
- gl::Error error = useLevelZeroWorkaroundTexture(mipLevels == 1);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(useLevelZeroWorkaroundTexture(context, mipLevels == 1));
}
if (swizzleRequired)
{
- verifySwizzleExists(textureState.swizzleRed, textureState.swizzleGreen,
- textureState.swizzleBlue, textureState.swizzleAlpha);
+ verifySwizzleExists(textureState.getSwizzleState());
}
- SRVKey key(textureState.baseLevel, mipLevels, swizzleRequired);
+ // We drop the stencil when sampling from the SRV if three conditions hold:
+ // 1. the drop stencil workaround is enabled.
+ bool workaround = mRenderer->getWorkarounds().emulateTinyStencilTextures;
+ // 2. this is a stencil texture.
+ bool hasStencil = (mFormatInfo.format().stencilBits > 0);
+ // 3. the texture has a 1x1 or 2x2 mip.
+ int effectiveTopLevel = effectiveBaseLevel + mipLevels - 1;
+ bool hasSmallMips =
+ (getLevelWidth(effectiveTopLevel) <= 2 || getLevelHeight(effectiveTopLevel) <= 2);
+
+ bool useDropStencil = (workaround && hasStencil && hasSmallMips);
+ SRVKey key(effectiveBaseLevel, mipLevels, swizzleRequired, useDropStencil);
+ if (useDropStencil)
+ {
+ // Ensure drop texture gets created.
+ DropStencil result = DropStencil::CREATED;
+ ANGLE_TRY_RESULT(ensureDropStencilTexture(context), result);
+
+ // Clear the SRV cache if necessary.
+ // TODO(jmadill): Re-use find query result.
+ auto srvEntry = mSrvCache.find(key);
+ if (result == DropStencil::CREATED && srvEntry != mSrvCache.end())
+ {
+ mSrvCache.erase(key);
+ }
+ }
+
+ ANGLE_TRY(getCachedOrCreateSRV(context, key, outSRV));
+
+ return gl::NoError();
+}
+
+gl::Error TextureStorage11::getCachedOrCreateSRV(const gl::Context *context,
+ const SRVKey &key,
+ const d3d11::SharedSRV **outSRV)
+{
auto iter = mSrvCache.find(key);
if (iter != mSrvCache.end())
{
- *outSRV = iter->second;
- return gl::Error(GL_NO_ERROR);
+ *outSRV = &iter->second;
+ return gl::NoError();
}
- ID3D11Resource *texture = nullptr;
- if (swizzleRequired)
+ const TextureHelper11 *texture = nullptr;
+ DXGI_FORMAT format = DXGI_FORMAT_UNKNOWN;
+
+ if (key.swizzle)
{
- gl::Error error = getSwizzleTexture(&texture);
- if (error.isError())
- {
- return error;
- }
+ const auto &swizzleFormat =
+ mFormatInfo.getSwizzleFormat(mRenderer->getRenderer11DeviceCaps());
+ ASSERT(!key.dropStencil || swizzleFormat.format().stencilBits == 0);
+ ANGLE_TRY(getSwizzleTexture(&texture));
+ format = swizzleFormat.srvFormat;
}
- else
+ else if (key.dropStencil)
{
- gl::Error error = getResource(&texture);
- if (error.isError())
- {
- return error;
- }
+ ASSERT(mDropStencilTexture.valid());
+ texture = &mDropStencilTexture;
+ format = DXGI_FORMAT_R32_FLOAT;
}
-
- ID3D11ShaderResourceView *srv = nullptr;
- DXGI_FORMAT format = (swizzleRequired ? mSwizzleShaderResourceFormat : mShaderResourceFormat);
- gl::Error error = createSRV(textureState.baseLevel, mipLevels, format, texture, &srv);
- if (error.isError())
+ else
{
- return error;
+ ANGLE_TRY(getResource(context, &texture));
+ format = mFormatInfo.srvFormat;
}
- mSrvCache.insert(std::make_pair(key, srv));
- *outSRV = srv;
+ d3d11::SharedSRV srv;
+
+ ANGLE_TRY(createSRV(context, key.baseLevel, key.mipLevels, format, *texture, &srv));
+
+ const auto &insertIt = mSrvCache.insert(std::make_pair(key, std::move(srv)));
+ *outSRV = &insertIt.first->second;
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error TextureStorage11::getSRVLevel(int mipLevel, ID3D11ShaderResourceView **outSRV)
+gl::Error TextureStorage11::getSRVLevel(const gl::Context *context,
+ int mipLevel,
+ bool blitSRV,
+ const d3d11::SharedSRV **outSRV)
{
ASSERT(mipLevel >= 0 && mipLevel < getLevelCount());
- if (!mLevelSRVs[mipLevel])
+ auto &levelSRVs = (blitSRV) ? mLevelBlitSRVs : mLevelSRVs;
+ auto &otherLevelSRVs = (blitSRV) ? mLevelSRVs : mLevelBlitSRVs;
+
+ if (!levelSRVs[mipLevel].valid())
{
- ID3D11Resource *resource = NULL;
- gl::Error error = getResource(&resource);
- if (error.isError())
+ // Only create a different SRV for blit if blit format is different from regular srv format
+ if (otherLevelSRVs[mipLevel].valid() && mFormatInfo.srvFormat == mFormatInfo.blitSRVFormat)
{
- return error;
+ levelSRVs[mipLevel] = otherLevelSRVs[mipLevel].makeCopy();
}
-
- error = createSRV(mipLevel, 1, mShaderResourceFormat, resource, &mLevelSRVs[mipLevel]);
- if (error.isError())
+ else
{
- return error;
+ const TextureHelper11 *resource = nullptr;
+ ANGLE_TRY(getResource(context, &resource));
+
+ DXGI_FORMAT resourceFormat =
+ blitSRV ? mFormatInfo.blitSRVFormat : mFormatInfo.srvFormat;
+ ANGLE_TRY(
+ createSRV(context, mipLevel, 1, resourceFormat, *resource, &levelSRVs[mipLevel]));
}
}
- *outSRV = mLevelSRVs[mipLevel];
+ *outSRV = &levelSRVs[mipLevel];
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error TextureStorage11::getSRVLevels(GLint baseLevel, GLint maxLevel, ID3D11ShaderResourceView **outSRV)
+gl::Error TextureStorage11::getSRVLevels(const gl::Context *context,
+ GLint baseLevel,
+ GLint maxLevel,
+ const d3d11::SharedSRV **outSRV)
{
unsigned int mipLevels = maxLevel - baseLevel + 1;
- // Make sure there's 'mipLevels' mipmap levels below the base level (offset by the top level, which corresponds to GL level 0)
+ // Make sure there's 'mipLevels' mipmap levels below the base level (offset by the top level,
+ // which corresponds to GL level 0)
mipLevels = std::min(mipLevels, mMipLevels - mTopLevel - baseLevel);
if (mRenderer->getRenderer11DeviceCaps().featureLevel <= D3D_FEATURE_LEVEL_9_3)
@@ -310,245 +367,218 @@ gl::Error TextureStorage11::getSRVLevels(GLint baseLevel, GLint maxLevel, ID3D11
if (mRenderer->getWorkarounds().zeroMaxLodWorkaround)
{
// We must ensure that the level zero texture is in sync with mipped texture.
- gl::Error error = useLevelZeroWorkaroundTexture(mipLevels == 1);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(useLevelZeroWorkaroundTexture(context, mipLevels == 1));
}
- SRVKey key(baseLevel, mipLevels, false);
- auto iter = mSrvCache.find(key);
- if (iter != mSrvCache.end())
- {
- *outSRV = iter->second;
- return gl::Error(GL_NO_ERROR);
- }
+ // TODO(jmadill): Assert we don't need to drop stencil.
- ID3D11Resource *texture = nullptr;
- gl::Error error = getResource(&texture);
- if (error.isError())
- {
- return error;
- }
+ SRVKey key(baseLevel, mipLevels, false, false);
+ ANGLE_TRY(getCachedOrCreateSRV(context, key, outSRV));
- ID3D11ShaderResourceView *srv = nullptr;
- error = createSRV(baseLevel, mipLevels, mShaderResourceFormat, texture, &srv);
- if (error.isError())
- {
- return error;
- }
-
- mSrvCache[key] = srv;
- *outSRV = srv;
+ return gl::NoError();
+}
- return gl::Error(GL_NO_ERROR);
+const d3d11::Format &TextureStorage11::getFormatSet() const
+{
+ return mFormatInfo;
}
-gl::Error TextureStorage11::generateSwizzles(GLenum swizzleRed, GLenum swizzleGreen, GLenum swizzleBlue, GLenum swizzleAlpha)
+gl::Error TextureStorage11::generateSwizzles(const gl::Context *context,
+ const gl::SwizzleState &swizzleTarget)
{
- SwizzleCacheValue swizzleTarget(swizzleRed, swizzleGreen, swizzleBlue, swizzleAlpha);
for (int level = 0; level < getLevelCount(); level++)
{
// Check if the swizzle for this level is out of date
if (mSwizzleCache[level] != swizzleTarget)
{
// Need to re-render the swizzle for this level
- ID3D11ShaderResourceView *sourceSRV = NULL;
- gl::Error error = getSRVLevel(level, &sourceSRV);
- if (error.isError())
- {
- return error;
- }
+ const d3d11::SharedSRV *sourceSRV = nullptr;
+ ANGLE_TRY(getSRVLevel(context, level, true, &sourceSRV));
- ID3D11RenderTargetView *destRTV = NULL;
- error = getSwizzleRenderTarget(level, &destRTV);
- if (error.isError())
- {
- return error;
- }
+ const d3d11::RenderTargetView *destRTV;
+ ANGLE_TRY(getSwizzleRenderTarget(level, &destRTV));
gl::Extents size(getLevelWidth(level), getLevelHeight(level), getLevelDepth(level));
Blit11 *blitter = mRenderer->getBlitter();
- error = blitter->swizzleTexture(sourceSRV, destRTV, size, swizzleRed, swizzleGreen, swizzleBlue, swizzleAlpha);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(blitter->swizzleTexture(context, *sourceSRV, *destRTV, size, swizzleTarget));
mSwizzleCache[level] = swizzleTarget;
}
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-void TextureStorage11::invalidateSwizzleCacheLevel(int mipLevel)
+void TextureStorage11::markLevelDirty(int mipLevel)
{
- if (mipLevel >= 0 && static_cast<unsigned int>(mipLevel) < ArraySize(mSwizzleCache))
+ if (mipLevel >= 0 && static_cast<size_t>(mipLevel) < mSwizzleCache.size())
{
- // The default constructor of SwizzleCacheValue has GL_NONE for all channels which is not a
- // valid swizzle combination
- mSwizzleCache[mipLevel] = SwizzleCacheValue();
+ // The default constructor of SwizzleState has GL_INVALID_INDEX for all channels which is
+ // not a valid swizzle combination
+ if (mSwizzleCache[mipLevel] != gl::SwizzleState())
+ {
+ // TODO(jmadill): Invalidate specific swizzle.
+ mRenderer->getStateManager()->invalidateSwizzles();
+ mSwizzleCache[mipLevel] = gl::SwizzleState();
+ }
+ }
+
+ if (mDropStencilTexture.valid())
+ {
+ mDropStencilTexture.reset();
}
}
-void TextureStorage11::invalidateSwizzleCache()
+void TextureStorage11::markDirty()
{
- for (unsigned int mipLevel = 0; mipLevel < ArraySize(mSwizzleCache); mipLevel++)
+ for (size_t mipLevel = 0; mipLevel < mSwizzleCache.size(); ++mipLevel)
{
- invalidateSwizzleCacheLevel(mipLevel);
+ markLevelDirty(static_cast<int>(mipLevel));
}
}
-gl::Error TextureStorage11::updateSubresourceLevel(ID3D11Resource *srcTexture, unsigned int sourceSubresource,
- const gl::ImageIndex &index, const gl::Box &copyArea)
+gl::Error TextureStorage11::updateSubresourceLevel(const gl::Context *context,
+ const TextureHelper11 &srcTexture,
+ unsigned int sourceSubresource,
+ const gl::ImageIndex &index,
+ const gl::Box &copyArea)
{
- ASSERT(srcTexture);
+ ASSERT(srcTexture.valid());
- GLint level = index.mipIndex;
+ const GLint level = index.mipIndex;
- invalidateSwizzleCacheLevel(level);
+ markLevelDirty(level);
gl::Extents texSize(getLevelWidth(level), getLevelHeight(level), getLevelDepth(level));
- bool fullCopy = copyArea.x == 0 &&
- copyArea.y == 0 &&
- copyArea.z == 0 &&
- copyArea.width == texSize.width &&
- copyArea.height == texSize.height &&
- copyArea.depth == texSize.depth;
+ bool fullCopy = copyArea.x == 0 && copyArea.y == 0 && copyArea.z == 0 &&
+ copyArea.width == texSize.width && copyArea.height == texSize.height &&
+ copyArea.depth == texSize.depth;
- ID3D11Resource *dstTexture = NULL;
- gl::Error error(GL_NO_ERROR);
+ const TextureHelper11 *dstTexture = nullptr;
- // If the zero-LOD workaround is active and we want to update a level greater than zero, then we should
- // update the mipmapped texture, even if mapmaps are currently disabled.
+ // If the zero-LOD workaround is active and we want to update a level greater than zero, then we
+ // should update the mipmapped texture, even if mapmaps are currently disabled.
if (index.mipIndex > 0 && mRenderer->getWorkarounds().zeroMaxLodWorkaround)
{
- error = getMippedResource(&dstTexture);
+ ANGLE_TRY(getMippedResource(context, &dstTexture));
}
else
{
- error = getResource(&dstTexture);
- }
-
- if (error.isError())
- {
- return error;
+ ANGLE_TRY(getResource(context, &dstTexture));
}
unsigned int dstSubresource = getSubresourceIndex(index);
- ASSERT(dstTexture);
+ ASSERT(dstTexture->valid());
- const d3d11::DXGIFormat &dxgiFormatInfo = d3d11::GetDXGIFormatInfo(mTextureFormat);
- if (!fullCopy && (dxgiFormatInfo.depthBits > 0 || dxgiFormatInfo.stencilBits > 0))
+ const d3d11::DXGIFormatSize &dxgiFormatSizeInfo =
+ d3d11::GetDXGIFormatSizeInfo(mFormatInfo.texFormat);
+ if (!fullCopy && mFormatInfo.dsvFormat != DXGI_FORMAT_UNKNOWN)
{
// CopySubresourceRegion cannot copy partial depth stencils, use the blitter instead
- Blit11 *blitter = mRenderer->getBlitter();
-
+ Blit11 *blitter = mRenderer->getBlitter();
return blitter->copyDepthStencil(srcTexture, sourceSubresource, copyArea, texSize,
- dstTexture, dstSubresource, copyArea, texSize,
- NULL);
+ *dstTexture, dstSubresource, copyArea, texSize, nullptr);
}
- else
- {
- D3D11_BOX srcBox;
- srcBox.left = copyArea.x;
- srcBox.top = copyArea.y;
- srcBox.right = copyArea.x + roundUp(static_cast<UINT>(copyArea.width), dxgiFormatInfo.blockWidth);
- srcBox.bottom = copyArea.y + roundUp(static_cast<UINT>(copyArea.height), dxgiFormatInfo.blockHeight);
- srcBox.front = copyArea.z;
- srcBox.back = copyArea.z + copyArea.depth;
- ID3D11DeviceContext *context = mRenderer->getDeviceContext();
+ D3D11_BOX srcBox;
+ srcBox.left = copyArea.x;
+ srcBox.top = copyArea.y;
+ srcBox.right =
+ copyArea.x + roundUp(static_cast<UINT>(copyArea.width), dxgiFormatSizeInfo.blockWidth);
+ srcBox.bottom =
+ copyArea.y + roundUp(static_cast<UINT>(copyArea.height), dxgiFormatSizeInfo.blockHeight);
+ srcBox.front = copyArea.z;
+ srcBox.back = copyArea.z + copyArea.depth;
- context->CopySubresourceRegion(dstTexture, dstSubresource, copyArea.x, copyArea.y, copyArea.z,
- srcTexture, sourceSubresource, fullCopy ? NULL : &srcBox);
- return gl::Error(GL_NO_ERROR);
- }
+ ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
+
+ deviceContext->CopySubresourceRegion(dstTexture->get(), dstSubresource, copyArea.x, copyArea.y,
+ copyArea.z, srcTexture.get(), sourceSubresource,
+ fullCopy ? nullptr : &srcBox);
+ return gl::NoError();
}
-gl::Error TextureStorage11::copySubresourceLevel(ID3D11Resource* dstTexture, unsigned int dstSubresource,
- const gl::ImageIndex &index, const gl::Box &region)
+gl::Error TextureStorage11::copySubresourceLevel(const gl::Context *context,
+ const TextureHelper11 &dstTexture,
+ unsigned int dstSubresource,
+ const gl::ImageIndex &index,
+ const gl::Box &region)
{
- ASSERT(dstTexture);
+ ASSERT(dstTexture.valid());
- ID3D11Resource *srcTexture = NULL;
- gl::Error error(GL_NO_ERROR);
+ const TextureHelper11 *srcTexture = nullptr;
- // If the zero-LOD workaround is active and we want to update a level greater than zero, then we should
- // update the mipmapped texture, even if mapmaps are currently disabled.
+ // If the zero-LOD workaround is active and we want to update a level greater than zero, then we
+ // should update the mipmapped texture, even if mapmaps are currently disabled.
if (index.mipIndex > 0 && mRenderer->getWorkarounds().zeroMaxLodWorkaround)
{
- error = getMippedResource(&srcTexture);
+ ANGLE_TRY(getMippedResource(context, &srcTexture));
}
else
{
- error = getResource(&srcTexture);
+ ANGLE_TRY(getResource(context, &srcTexture));
}
- if (error.isError())
- {
- return error;
- }
-
- ASSERT(srcTexture);
+ ASSERT(srcTexture->valid());
unsigned int srcSubresource = getSubresourceIndex(index);
- ID3D11DeviceContext *context = mRenderer->getDeviceContext();
+ ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
- // D3D11 can't perform partial CopySubresourceRegion on depth/stencil textures, so pSrcBox should be NULL.
+ // D3D11 can't perform partial CopySubresourceRegion on depth/stencil textures, so pSrcBox
+ // should be nullptr.
D3D11_BOX srcBox;
- D3D11_BOX *pSrcBox = NULL;
+ D3D11_BOX *pSrcBox = nullptr;
if (mRenderer->getRenderer11DeviceCaps().featureLevel <= D3D_FEATURE_LEVEL_9_3)
{
- // However, D3D10Level9 doesn't always perform CopySubresourceRegion correctly unless the source box
- // is specified. This is okay, since we don't perform CopySubresourceRegion on depth/stencil
- // textures on 9_3.
- ASSERT(d3d11::GetDXGIFormatInfo(mTextureFormat).depthBits == 0);
- ASSERT(d3d11::GetDXGIFormatInfo(mTextureFormat).stencilBits == 0);
- srcBox.left = region.x;
- srcBox.right = region.x + region.width;
- srcBox.top = region.y;
- srcBox.bottom = region.y + region.height;
- srcBox.front = region.z;
- srcBox.back = region.z + region.depth;
- pSrcBox = &srcBox;
+ GLsizei width = region.width;
+ GLsizei height = region.height;
+ d3d11::MakeValidSize(false, mFormatInfo.texFormat, &width, &height, nullptr);
+
+ // Keep srcbox as nullptr if we're dealing with tiny mips of compressed textures.
+ if (width == region.width && height == region.height)
+ {
+ // However, D3D10Level9 doesn't always perform CopySubresourceRegion correctly unless
+ // the source box is specified. This is okay, since we don't perform
+ // CopySubresourceRegion on depth/stencil textures on 9_3.
+ ASSERT(mFormatInfo.dsvFormat == DXGI_FORMAT_UNKNOWN);
+ srcBox.left = region.x;
+ srcBox.right = region.x + region.width;
+ srcBox.top = region.y;
+ srcBox.bottom = region.y + region.height;
+ srcBox.front = region.z;
+ srcBox.back = region.z + region.depth;
+ pSrcBox = &srcBox;
+ }
}
- context->CopySubresourceRegion(dstTexture, dstSubresource, region.x, region.y, region.z,
- srcTexture, srcSubresource, pSrcBox);
+ deviceContext->CopySubresourceRegion(dstTexture.get(), dstSubresource, region.x, region.y,
+ region.z, srcTexture->get(), srcSubresource, pSrcBox);
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error TextureStorage11::generateMipmap(const gl::ImageIndex &sourceIndex, const gl::ImageIndex &destIndex)
+gl::Error TextureStorage11::generateMipmap(const gl::Context *context,
+ const gl::ImageIndex &sourceIndex,
+ const gl::ImageIndex &destIndex)
{
ASSERT(sourceIndex.layerIndex == destIndex.layerIndex);
- invalidateSwizzleCacheLevel(destIndex.mipIndex);
+ markLevelDirty(destIndex.mipIndex);
- RenderTargetD3D *source = NULL;
- gl::Error error = getRenderTarget(sourceIndex, &source);
- if (error.isError())
- {
- return error;
- }
+ RenderTargetD3D *source = nullptr;
+ ANGLE_TRY(getRenderTarget(context, sourceIndex, &source));
- RenderTargetD3D *dest = NULL;
- error = getRenderTarget(destIndex, &dest);
- if (error.isError())
- {
- return error;
- }
+ RenderTargetD3D *dest = nullptr;
+ ANGLE_TRY(getRenderTarget(context, destIndex, &dest));
- ID3D11ShaderResourceView *sourceSRV = GetAs<RenderTarget11>(source)->getShaderResourceView();
- ID3D11RenderTargetView *destRTV = GetAs<RenderTarget11>(dest)->getRenderTargetView();
+ RenderTarget11 *rt11 = GetAs<RenderTarget11>(source);
+ const d3d11::SharedSRV &sourceSRV = rt11->getBlitShaderResourceView();
+ const d3d11::RenderTargetView &destRTV = rt11->getRenderTargetView();
gl::Box sourceArea(0, 0, 0, source->getWidth(), source->getHeight(), source->getDepth());
gl::Extents sourceSize(source->getWidth(), source->getHeight(), source->getDepth());
@@ -557,90 +587,75 @@ gl::Error TextureStorage11::generateMipmap(const gl::ImageIndex &sourceIndex, co
gl::Extents destSize(dest->getWidth(), dest->getHeight(), dest->getDepth());
Blit11 *blitter = mRenderer->getBlitter();
- return blitter->copyTexture(sourceSRV, sourceArea, sourceSize, destRTV, destArea, destSize,
- NULL, gl::GetInternalFormatInfo(source->getInternalFormat()).format,
- GL_LINEAR, false);
+ GLenum format = gl::GetUnsizedFormat(source->getInternalFormat());
+ return blitter->copyTexture(context, sourceSRV, sourceArea, sourceSize, format, destRTV,
+ destArea, destSize, nullptr, format, GL_LINEAR, false, false,
+ false);
}
-void TextureStorage11::verifySwizzleExists(GLenum swizzleRed, GLenum swizzleGreen, GLenum swizzleBlue, GLenum swizzleAlpha)
+void TextureStorage11::verifySwizzleExists(const gl::SwizzleState &swizzleState)
{
- SwizzleCacheValue swizzleTarget(swizzleRed, swizzleGreen, swizzleBlue, swizzleAlpha);
for (unsigned int level = 0; level < mMipLevels; level++)
{
- ASSERT(mSwizzleCache[level] == swizzleTarget);
+ ASSERT(mSwizzleCache[level] == swizzleState);
}
}
void TextureStorage11::clearSRVCache()
{
- invalidateSwizzleCache();
-
- auto iter = mSrvCache.begin();
- while (iter != mSrvCache.end())
- {
- if (!iter->first.swizzle)
- {
- SafeRelease(iter->second);
- iter = mSrvCache.erase(iter);
- }
- else
- {
- iter++;
- }
- }
+ markDirty();
+ mSrvCache.clear();
- for (size_t level = 0; level < ArraySize(mLevelSRVs); level++)
+ for (size_t level = 0; level < mLevelSRVs.size(); level++)
{
- SafeRelease(mLevelSRVs[level]);
+ mLevelSRVs[level].reset();
+ mLevelBlitSRVs[level].reset();
}
}
-gl::Error TextureStorage11::copyToStorage(TextureStorage *destStorage)
+gl::Error TextureStorage11::copyToStorage(const gl::Context *context, TextureStorage *destStorage)
{
ASSERT(destStorage);
- ID3D11Resource *sourceResouce = NULL;
- gl::Error error = getResource(&sourceResouce);
- if (error.isError())
- {
- return error;
- }
+ const TextureHelper11 *sourceResouce = nullptr;
+ ANGLE_TRY(getResource(context, &sourceResouce));
- TextureStorage11 *dest11 = GetAs<TextureStorage11>(destStorage);
- ID3D11Resource *destResource = NULL;
- error = dest11->getResource(&destResource);
- if (error.isError())
- {
- return error;
- }
+ TextureStorage11 *dest11 = GetAs<TextureStorage11>(destStorage);
+ const TextureHelper11 *destResource = nullptr;
+ ANGLE_TRY(dest11->getResource(context, &destResource));
ID3D11DeviceContext *immediateContext = mRenderer->getDeviceContext();
- immediateContext->CopyResource(destResource, sourceResouce);
+ immediateContext->CopyResource(destResource->get(), sourceResouce->get());
- dest11->invalidateSwizzleCache();
+ dest11->markDirty();
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error TextureStorage11::setData(const gl::ImageIndex &index, ImageD3D *image, const gl::Box *destBox, GLenum type,
- const gl::PixelUnpackState &unpack, const uint8_t *pixelData)
+gl::Error TextureStorage11::setData(const gl::Context *context,
+ const gl::ImageIndex &index,
+ ImageD3D *image,
+ const gl::Box *destBox,
+ GLenum type,
+ const gl::PixelUnpackState &unpack,
+ const uint8_t *pixelData)
{
ASSERT(!image->isDirty());
- ID3D11Resource *resource = NULL;
- gl::Error error = getResource(&resource);
- if (error.isError())
- {
- return error;
- }
- ASSERT(resource);
+ markLevelDirty(index.mipIndex);
+
+ const TextureHelper11 *resource = nullptr;
+ ANGLE_TRY(getResource(context, &resource));
+ ASSERT(resource && resource->valid());
UINT destSubresource = getSubresourceIndex(index);
- const gl::InternalFormat &internalFormatInfo = gl::GetInternalFormatInfo(image->getInternalFormat());
+ const gl::InternalFormat &internalFormatInfo =
+ gl::GetInternalFormatInfo(image->getInternalFormat(), type);
- gl::Box levelBox(0, 0, 0, getLevelWidth(index.mipIndex), getLevelHeight(index.mipIndex), getLevelDepth(index.mipIndex));
- bool fullUpdate = (destBox == NULL || *destBox == levelBox);
+ gl::Box levelBox(0, 0, 0, getLevelWidth(index.mipIndex), getLevelHeight(index.mipIndex),
+ getLevelDepth(index.mipIndex));
+ bool fullUpdate = (destBox == nullptr || *destBox == levelBox);
ASSERT(internalFormatInfo.depthBits == 0 || fullUpdate);
// TODO(jmadill): Handle compressed formats
@@ -649,36 +664,44 @@ gl::Error TextureStorage11::setData(const gl::ImageIndex &index, ImageD3D *image
// with compressed formats in the calling logic.
ASSERT(!internalFormatInfo.compressed);
- int width = destBox ? destBox->width : static_cast<int>(image->getWidth());
- int height = destBox ? destBox->height : static_cast<int>(image->getHeight());
- int depth = destBox ? destBox->depth : static_cast<int>(image->getDepth());
- UINT srcRowPitch = internalFormatInfo.computeRowPitch(type, width, unpack.alignment, unpack.rowLength);
- UINT srcDepthPitch = internalFormatInfo.computeDepthPitch(type, width, height, unpack.alignment,
- unpack.rowLength, unpack.imageHeight);
- GLsizei srcSkipBytes = internalFormatInfo.computeSkipPixels(
- srcRowPitch, srcDepthPitch, unpack.skipImages, unpack.skipRows, unpack.skipPixels);
-
- const d3d11::TextureFormat &d3d11Format = d3d11::GetTextureFormatInfo(image->getInternalFormat(), mRenderer->getRenderer11DeviceCaps());
- const d3d11::DXGIFormat &dxgiFormatInfo = d3d11::GetDXGIFormatInfo(d3d11Format.texFormat);
-
- size_t outputPixelSize = dxgiFormatInfo.pixelBytes;
+ const int imageWidth = static_cast<int>(image->getWidth());
+ const int width = destBox ? destBox->width : imageWidth;
+ const int imageHeight = static_cast<int>(image->getHeight());
+ const int height = destBox ? destBox->height : imageHeight;
+ const int imageDepth = static_cast<int>(image->getDepth());
+ const int depth = destBox ? destBox->depth : imageDepth;
+ if (imageWidth < width || imageHeight < height || imageDepth < depth)
+ fullUpdate = true;
+ GLuint srcRowPitch = 0;
+ ANGLE_TRY_RESULT(
+ internalFormatInfo.computeRowPitch(type, width, unpack.alignment, unpack.rowLength),
+ srcRowPitch);
+ GLuint srcDepthPitch = 0;
+ ANGLE_TRY_RESULT(internalFormatInfo.computeDepthPitch(height, unpack.imageHeight, srcRowPitch),
+ srcDepthPitch);
+ GLuint srcSkipBytes = 0;
+ ANGLE_TRY_RESULT(
+ internalFormatInfo.computeSkipBytes(srcRowPitch, srcDepthPitch, unpack, index.is3D()),
+ srcSkipBytes);
+
+ const d3d11::Format &d3d11Format =
+ d3d11::Format::Get(image->getInternalFormat(), mRenderer->getRenderer11DeviceCaps());
+ const d3d11::DXGIFormatSize &dxgiFormatInfo =
+ d3d11::GetDXGIFormatSizeInfo(d3d11Format.texFormat);
+
+ const size_t outputPixelSize = dxgiFormatInfo.pixelBytes;
UINT bufferRowPitch = static_cast<unsigned int>(outputPixelSize) * width;
UINT bufferDepthPitch = bufferRowPitch * height;
- size_t neededSize = bufferDepthPitch * depth;
- MemoryBuffer *conversionBuffer = nullptr;
+ const size_t neededSize = bufferDepthPitch * depth;
+ angle::MemoryBuffer *conversionBuffer = nullptr;
const uint8_t *data = nullptr;
- d3d11::LoadImageFunctionInfo loadFunctionInfo = d3d11Format.loadFunctions.at(type);
+ LoadImageFunctionInfo loadFunctionInfo = d3d11Format.getLoadFunctions()(type);
if (loadFunctionInfo.requiresConversion)
{
- error = mRenderer->getScratchMemoryBuffer(neededSize, &conversionBuffer);
- if (error.isError())
- {
- return error;
- }
-
+ ANGLE_TRY(mRenderer->getScratchMemoryBuffer(neededSize, &conversionBuffer));
loadFunctionInfo.loadFunction(width, height, depth, pixelData + srcSkipBytes, srcRowPitch,
srcDepthPitch, conversionBuffer->data(), bufferRowPitch,
bufferDepthPitch);
@@ -698,264 +721,233 @@ gl::Error TextureStorage11::setData(const gl::ImageIndex &index, ImageD3D *image
ASSERT(destBox);
D3D11_BOX destD3DBox;
- destD3DBox.left = destBox->x;
- destD3DBox.right = destBox->x + destBox->width;
- destD3DBox.top = destBox->y;
+ destD3DBox.left = destBox->x;
+ destD3DBox.right = destBox->x + destBox->width;
+ destD3DBox.top = destBox->y;
destD3DBox.bottom = destBox->y + destBox->height;
- destD3DBox.front = destBox->z;
- destD3DBox.back = destBox->z + destBox->depth;
+ destD3DBox.front = destBox->z;
+ destD3DBox.back = destBox->z + destBox->depth;
- immediateContext->UpdateSubresource(resource, destSubresource, &destD3DBox, data,
+ immediateContext->UpdateSubresource(resource->get(), destSubresource, &destD3DBox, data,
bufferRowPitch, bufferDepthPitch);
}
else
{
- immediateContext->UpdateSubresource(resource, destSubresource, NULL, data, bufferRowPitch,
- bufferDepthPitch);
+ immediateContext->UpdateSubresource(resource->get(), destSubresource, nullptr, data,
+ bufferRowPitch, bufferDepthPitch);
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
+}
+
+gl::ErrorOrResult<TextureStorage11::DropStencil> TextureStorage11::ensureDropStencilTexture(
+ const gl::Context *context)
+{
+ UNIMPLEMENTED();
+ return gl::InternalError() << "Drop stencil texture not implemented.";
}
TextureStorage11_2D::TextureStorage11_2D(Renderer11 *renderer, SwapChain11 *swapchain)
- : TextureStorage11(renderer, D3D11_BIND_RENDER_TARGET | D3D11_BIND_SHADER_RESOURCE, 0),
+ : TextureStorage11(renderer,
+ D3D11_BIND_RENDER_TARGET | D3D11_BIND_SHADER_RESOURCE,
+ 0,
+ swapchain->getRenderTargetInternalFormat()),
mTexture(swapchain->getOffscreenTexture()),
- mLevelZeroTexture(NULL),
- mLevelZeroRenderTarget(NULL),
+ mLevelZeroTexture(),
+ mLevelZeroRenderTarget(nullptr),
mUseLevelZeroTexture(false),
- mSwizzleTexture(NULL)
+ mSwizzleTexture()
{
- mTexture->AddRef();
-
for (unsigned int i = 0; i < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS; i++)
{
- mAssociatedImages[i] = NULL;
- mRenderTarget[i] = NULL;
- mSwizzleRenderTargets[i] = NULL;
+ mAssociatedImages[i] = nullptr;
+ mRenderTarget[i] = nullptr;
}
D3D11_TEXTURE2D_DESC texDesc;
- mTexture->GetDesc(&texDesc);
- mMipLevels = texDesc.MipLevels;
- mTextureFormat = texDesc.Format;
- mTextureWidth = texDesc.Width;
+ mTexture.getDesc(&texDesc);
+ mMipLevels = texDesc.MipLevels;
+ mTextureWidth = texDesc.Width;
mTextureHeight = texDesc.Height;
- mTextureDepth = 1;
-
- mInternalFormat = swapchain->GetRenderTargetInternalFormat();
-
- ID3D11ShaderResourceView *srv = swapchain->getRenderTargetShaderResource();
- D3D11_SHADER_RESOURCE_VIEW_DESC srvDesc;
- srv->GetDesc(&srvDesc);
- mShaderResourceFormat = srvDesc.Format;
-
- ID3D11RenderTargetView* offscreenRTV = swapchain->getRenderTarget();
- D3D11_RENDER_TARGET_VIEW_DESC rtvDesc;
- offscreenRTV->GetDesc(&rtvDesc);
- mRenderTargetFormat = rtvDesc.Format;
-
- const d3d11::DXGIFormat &dxgiFormatInfo = d3d11::GetDXGIFormatInfo(mTextureFormat);
- const d3d11::TextureFormat &formatInfo = d3d11::GetTextureFormatInfo(dxgiFormatInfo.internalFormat, mRenderer->getRenderer11DeviceCaps());
- mSwizzleTextureFormat = formatInfo.swizzleTexFormat;
- mSwizzleShaderResourceFormat = formatInfo.swizzleSRVFormat;
- mSwizzleRenderTargetFormat = formatInfo.swizzleRTVFormat;
-
- mDepthStencilFormat = DXGI_FORMAT_UNKNOWN;
-}
-
-TextureStorage11_2D::TextureStorage11_2D(Renderer11 *renderer, GLenum internalformat, bool renderTarget, GLsizei width, GLsizei height, int levels, bool hintLevelZeroOnly)
- : TextureStorage11(renderer,
- GetTextureBindFlags(internalformat, renderer->getRenderer11DeviceCaps(), renderTarget),
- GetTextureMiscFlags(internalformat, renderer->getRenderer11DeviceCaps(), renderTarget, levels)),
- mTexture(NULL),
- mLevelZeroTexture(NULL),
- mLevelZeroRenderTarget(NULL),
- mUseLevelZeroTexture(false),
- mSwizzleTexture(NULL)
+ mTextureDepth = 1;
+ mHasKeyedMutex = (texDesc.MiscFlags & D3D11_RESOURCE_MISC_SHARED_KEYEDMUTEX) != 0;
+}
+
+TextureStorage11_2D::TextureStorage11_2D(Renderer11 *renderer,
+ GLenum internalformat,
+ bool renderTarget,
+ GLsizei width,
+ GLsizei height,
+ int levels,
+ bool hintLevelZeroOnly)
+ : TextureStorage11(
+ renderer,
+ GetTextureBindFlags(internalformat, renderer->getRenderer11DeviceCaps(), renderTarget),
+ GetTextureMiscFlags(internalformat,
+ renderer->getRenderer11DeviceCaps(),
+ renderTarget,
+ levels),
+ internalformat),
+ mTexture(),
+ mHasKeyedMutex(false),
+ mLevelZeroTexture(),
+ mLevelZeroRenderTarget(nullptr),
+ mUseLevelZeroTexture(hintLevelZeroOnly && levels > 1),
+ mSwizzleTexture()
{
for (unsigned int i = 0; i < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS; i++)
{
- mAssociatedImages[i] = NULL;
- mRenderTarget[i] = NULL;
- mSwizzleRenderTargets[i] = NULL;
+ mAssociatedImages[i] = nullptr;
+ mRenderTarget[i] = nullptr;
}
- mInternalFormat = internalformat;
-
- const d3d11::TextureFormat &formatInfo = d3d11::GetTextureFormatInfo(internalformat, renderer->getRenderer11DeviceCaps());
- mTextureFormat = formatInfo.texFormat;
- mShaderResourceFormat = formatInfo.srvFormat;
- mDepthStencilFormat = formatInfo.dsvFormat;
- mRenderTargetFormat = formatInfo.rtvFormat;
- mSwizzleTextureFormat = formatInfo.swizzleTexFormat;
- mSwizzleShaderResourceFormat = formatInfo.swizzleSRVFormat;
- mSwizzleRenderTargetFormat = formatInfo.swizzleRTVFormat;
-
- d3d11::MakeValidSize(false, mTextureFormat, &width, &height, &mTopLevel);
- mMipLevels = mTopLevel + levels;
- mTextureWidth = width;
+ d3d11::MakeValidSize(false, mFormatInfo.texFormat, &width, &height, &mTopLevel);
+ mMipLevels = mTopLevel + levels;
+ mTextureWidth = width;
mTextureHeight = height;
- mTextureDepth = 1;
+ mTextureDepth = 1;
- if (hintLevelZeroOnly && levels > 1)
- {
- //The LevelZeroOnly hint should only be true if the zero max LOD workaround is active.
- ASSERT(mRenderer->getWorkarounds().zeroMaxLodWorkaround);
- mUseLevelZeroTexture = true;
- }
+ // The LevelZeroOnly hint should only be true if the zero max LOD workaround is active.
+ ASSERT(!mUseLevelZeroTexture || mRenderer->getWorkarounds().zeroMaxLodWorkaround);
}
-TextureStorage11_2D::~TextureStorage11_2D()
+gl::Error TextureStorage11_2D::onDestroy(const gl::Context *context)
{
for (unsigned i = 0; i < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS; i++)
{
- if (mAssociatedImages[i] != NULL)
+ if (mAssociatedImages[i] != nullptr)
{
- bool imageAssociationCorrect = mAssociatedImages[i]->isAssociatedStorageValid(this);
- ASSERT(imageAssociationCorrect);
+ mAssociatedImages[i]->verifyAssociatedStorageValid(this);
- if (imageAssociationCorrect)
- {
- // We must let the Images recover their data before we delete it from the TextureStorage.
- gl::Error error = mAssociatedImages[i]->recoverFromAssociatedStorage();
- if (error.isError())
- {
- // TODO: Find a way to report this back to the context
- }
- }
+ // We must let the Images recover their data before we delete it from the
+ // TextureStorage.
+ ANGLE_TRY(mAssociatedImages[i]->recoverFromAssociatedStorage(context));
}
}
- SafeRelease(mTexture);
- SafeRelease(mSwizzleTexture);
-
- SafeRelease(mLevelZeroTexture);
- SafeDelete(mLevelZeroRenderTarget);
-
- for (unsigned int i = 0; i < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS; i++)
+ if (mHasKeyedMutex)
{
- SafeDelete(mRenderTarget[i]);
- SafeRelease(mSwizzleRenderTargets[i]);
+ // If the keyed mutex is released that will unbind it and cause the state cache to become
+ // desynchronized.
+ mRenderer->getStateManager()->invalidateBoundViews();
}
+
+ // Invalidate RenderTargets.
+ InvalidateRenderTargetContainer(context, &mRenderTarget);
+ InvalidateRenderTarget(context, mLevelZeroRenderTarget.get());
+
+ return gl::NoError();
+}
+
+TextureStorage11_2D::~TextureStorage11_2D()
+{
}
-gl::Error TextureStorage11_2D::copyToStorage(TextureStorage *destStorage)
+gl::Error TextureStorage11_2D::copyToStorage(const gl::Context *context,
+ TextureStorage *destStorage)
{
ASSERT(destStorage);
- TextureStorage11_2D *dest11 = GetAs<TextureStorage11_2D>(destStorage);
+ TextureStorage11_2D *dest11 = GetAs<TextureStorage11_2D>(destStorage);
+ ID3D11DeviceContext *immediateContext = mRenderer->getDeviceContext();
if (mRenderer->getWorkarounds().zeroMaxLodWorkaround)
{
- ID3D11DeviceContext *immediateContext = mRenderer->getDeviceContext();
-
- // If either mTexture or mLevelZeroTexture exist, then we need to copy them into the corresponding textures in destStorage.
- if (mTexture)
+ // If either mTexture or mLevelZeroTexture exist, then we need to copy them into the
+ // corresponding textures in destStorage.
+ if (mTexture.valid())
{
- gl::Error error = dest11->useLevelZeroWorkaroundTexture(false);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(dest11->useLevelZeroWorkaroundTexture(context, false));
- ID3D11Resource *destResource = NULL;
- error = dest11->getResource(&destResource);
- if (error.isError())
- {
- return error;
- }
+ const TextureHelper11 *destResource = nullptr;
+ ANGLE_TRY(dest11->getResource(context, &destResource));
- immediateContext->CopyResource(destResource, mTexture);
+ immediateContext->CopyResource(destResource->get(), mTexture.get());
}
- if (mLevelZeroTexture)
+ if (mLevelZeroTexture.valid())
{
- gl::Error error = dest11->useLevelZeroWorkaroundTexture(true);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(dest11->useLevelZeroWorkaroundTexture(context, true));
- ID3D11Resource *destResource = NULL;
- error = dest11->getResource(&destResource);
- if (error.isError())
- {
- return error;
- }
+ const TextureHelper11 *destResource = nullptr;
+ ANGLE_TRY(dest11->getResource(context, &destResource));
- immediateContext->CopyResource(destResource, mLevelZeroTexture);
+ immediateContext->CopyResource(destResource->get(), mLevelZeroTexture.get());
}
+
+ return gl::NoError();
}
- else
- {
- ID3D11Resource *sourceResouce = NULL;
- gl::Error error = getResource(&sourceResouce);
- if (error.isError())
- {
- return error;
- }
- ID3D11Resource *destResource = NULL;
- error = dest11->getResource(&destResource);
- if (error.isError())
- {
- return error;
- }
+ const TextureHelper11 *sourceResouce = nullptr;
+ ANGLE_TRY(getResource(context, &sourceResouce));
- ID3D11DeviceContext *immediateContext = mRenderer->getDeviceContext();
- immediateContext->CopyResource(destResource, sourceResouce);
- }
+ const TextureHelper11 *destResource = nullptr;
+ ANGLE_TRY(dest11->getResource(context, &destResource));
- dest11->invalidateSwizzleCache();
+ immediateContext->CopyResource(destResource->get(), sourceResouce->get());
+ dest11->markDirty();
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error TextureStorage11_2D::useLevelZeroWorkaroundTexture(bool useLevelZeroTexture)
+gl::Error TextureStorage11_2D::useLevelZeroWorkaroundTexture(const gl::Context *context,
+ bool useLevelZeroTexture)
{
+ bool lastSetting = mUseLevelZeroTexture;
+
if (useLevelZeroTexture && mMipLevels > 1)
{
- if (!mUseLevelZeroTexture && mTexture)
+ if (!mUseLevelZeroTexture && mTexture.valid())
{
- gl::Error error = ensureTextureExists(1);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(ensureTextureExists(1));
// Pull data back from the mipped texture if necessary.
- ASSERT(mLevelZeroTexture);
- ID3D11DeviceContext *context = mRenderer->getDeviceContext();
- context->CopySubresourceRegion(mLevelZeroTexture, 0, 0, 0, 0, mTexture, 0, NULL);
+ ASSERT(mLevelZeroTexture.valid());
+ ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
+ deviceContext->CopySubresourceRegion(mLevelZeroTexture.get(), 0, 0, 0, 0,
+ mTexture.get(), 0, nullptr);
}
mUseLevelZeroTexture = true;
}
else
{
- if (mUseLevelZeroTexture && mLevelZeroTexture)
+ if (mUseLevelZeroTexture && mLevelZeroTexture.valid())
{
- gl::Error error = ensureTextureExists(mMipLevels);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(ensureTextureExists(mMipLevels));
// Pull data back from the level zero texture if necessary.
- ASSERT(mTexture);
- ID3D11DeviceContext *context = mRenderer->getDeviceContext();
- context->CopySubresourceRegion(mTexture, 0, 0, 0, 0, mLevelZeroTexture, 0, NULL);
+ ASSERT(mTexture.valid());
+ ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
+ deviceContext->CopySubresourceRegion(mTexture.get(), 0, 0, 0, 0,
+ mLevelZeroTexture.get(), 0, nullptr);
}
mUseLevelZeroTexture = false;
}
- return gl::Error(GL_NO_ERROR);
+ if (lastSetting != mUseLevelZeroTexture)
+ {
+ // Mark everything as dirty to be conservative.
+ if (mLevelZeroRenderTarget)
+ {
+ mLevelZeroRenderTarget->signalDirty(context);
+ }
+ for (auto &renderTarget : mRenderTarget)
+ {
+ if (renderTarget)
+ {
+ renderTarget->signalDirty(context);
+ }
+ }
+ }
+
+ return gl::NoError();
}
-void TextureStorage11_2D::associateImage(Image11* image, const gl::ImageIndex &index)
+void TextureStorage11_2D::associateImage(Image11 *image, const gl::ImageIndex &index)
{
- GLint level = index.mipIndex;
+ const GLint level = index.mipIndex;
ASSERT(0 <= level && level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS);
@@ -965,539 +957,569 @@ void TextureStorage11_2D::associateImage(Image11* image, const gl::ImageIndex &i
}
}
-bool TextureStorage11_2D::isAssociatedImageValid(const gl::ImageIndex &index, Image11* expectedImage)
+void TextureStorage11_2D::verifyAssociatedImageValid(const gl::ImageIndex &index,
+ Image11 *expectedImage)
{
- GLint level = index.mipIndex;
+ const GLint level = index.mipIndex;
- if (0 <= level && level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS)
- {
- // This validation check should never return false. It means the Image/TextureStorage association is broken.
- bool retValue = (mAssociatedImages[level] == expectedImage);
- ASSERT(retValue);
- return retValue;
- }
-
- return false;
+ ASSERT(0 <= level && level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS);
+ // This validation check should never return false. It means the Image/TextureStorage
+ // association is broken.
+ ASSERT(mAssociatedImages[level] == expectedImage);
}
// disassociateImage allows an Image to end its association with a Storage.
-void TextureStorage11_2D::disassociateImage(const gl::ImageIndex &index, Image11* expectedImage)
+void TextureStorage11_2D::disassociateImage(const gl::ImageIndex &index, Image11 *expectedImage)
{
- GLint level = index.mipIndex;
+ const GLint level = index.mipIndex;
ASSERT(0 <= level && level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS);
-
- if (0 <= level && level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS)
- {
- ASSERT(mAssociatedImages[level] == expectedImage);
-
- if (mAssociatedImages[level] == expectedImage)
- {
- mAssociatedImages[level] = NULL;
- }
- }
+ ASSERT(mAssociatedImages[level] == expectedImage);
+ mAssociatedImages[level] = nullptr;
}
-// releaseAssociatedImage prepares the Storage for a new Image association. It lets the old Image recover its data before ending the association.
-gl::Error TextureStorage11_2D::releaseAssociatedImage(const gl::ImageIndex &index, Image11* incomingImage)
+// releaseAssociatedImage prepares the Storage for a new Image association. It lets the old Image
+// recover its data before ending the association.
+gl::Error TextureStorage11_2D::releaseAssociatedImage(const gl::Context *context,
+ const gl::ImageIndex &index,
+ Image11 *incomingImage)
{
- GLint level = index.mipIndex;
+ const GLint level = index.mipIndex;
ASSERT(0 <= level && level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS);
if (0 <= level && level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS)
{
// No need to let the old Image recover its data, if it is also the incoming Image.
- if (mAssociatedImages[level] != NULL && mAssociatedImages[level] != incomingImage)
+ if (mAssociatedImages[level] != nullptr && mAssociatedImages[level] != incomingImage)
{
- // Ensure that the Image is still associated with this TextureStorage. This should be true.
- bool imageAssociationCorrect = mAssociatedImages[level]->isAssociatedStorageValid(this);
- ASSERT(imageAssociationCorrect);
+ // Ensure that the Image is still associated with this TextureStorage.
+ mAssociatedImages[level]->verifyAssociatedStorageValid(this);
- if (imageAssociationCorrect)
- {
- // Force the image to recover from storage before its data is overwritten.
- // This will reset mAssociatedImages[level] to NULL too.
- gl::Error error = mAssociatedImages[level]->recoverFromAssociatedStorage();
- if (error.isError())
- {
- return error;
- }
- }
+ // Force the image to recover from storage before its data is overwritten.
+ // This will reset mAssociatedImages[level] to nullptr too.
+ ANGLE_TRY(mAssociatedImages[level]->recoverFromAssociatedStorage(context));
}
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error TextureStorage11_2D::getResource(ID3D11Resource **outResource)
+gl::Error TextureStorage11_2D::getResource(const gl::Context *context,
+ const TextureHelper11 **outResource)
{
if (mUseLevelZeroTexture && mMipLevels > 1)
{
- gl::Error error = ensureTextureExists(1);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(ensureTextureExists(1));
- *outResource = mLevelZeroTexture;
- return gl::Error(GL_NO_ERROR);
+ *outResource = &mLevelZeroTexture;
+ return gl::NoError();
}
- else
- {
- gl::Error error = ensureTextureExists(mMipLevels);
- if (error.isError())
- {
- return error;
- }
- *outResource = mTexture;
- return gl::Error(GL_NO_ERROR);
- }
+ ANGLE_TRY(ensureTextureExists(mMipLevels));
+
+ *outResource = &mTexture;
+ return gl::NoError();
}
-gl::Error TextureStorage11_2D::getMippedResource(ID3D11Resource **outResource)
+gl::Error TextureStorage11_2D::getMippedResource(const gl::Context *context,
+ const TextureHelper11 **outResource)
{
// This shouldn't be called unless the zero max LOD workaround is active.
ASSERT(mRenderer->getWorkarounds().zeroMaxLodWorkaround);
- gl::Error error = ensureTextureExists(mMipLevels);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(ensureTextureExists(mMipLevels));
- *outResource = mTexture;
- return gl::Error(GL_NO_ERROR);
+ *outResource = &mTexture;
+ return gl::NoError();
}
gl::Error TextureStorage11_2D::ensureTextureExists(int mipLevels)
{
// If mMipLevels = 1 then always use mTexture rather than mLevelZeroTexture.
- bool useLevelZeroTexture = mRenderer->getWorkarounds().zeroMaxLodWorkaround ? (mipLevels == 1) && (mMipLevels > 1) : false;
- ID3D11Texture2D **outputTexture = useLevelZeroTexture ? &mLevelZeroTexture : &mTexture;
+ bool useLevelZeroTexture = mRenderer->getWorkarounds().zeroMaxLodWorkaround
+ ? (mipLevels == 1) && (mMipLevels > 1)
+ : false;
+ TextureHelper11 *outputTexture = useLevelZeroTexture ? &mLevelZeroTexture : &mTexture;
// if the width or height is not positive this should be treated as an incomplete texture
// we handle that here by skipping the d3d texture creation
- if (*outputTexture == NULL && mTextureWidth > 0 && mTextureHeight > 0)
+ if (!outputTexture->valid() && mTextureWidth > 0 && mTextureHeight > 0)
{
ASSERT(mipLevels > 0);
- ID3D11Device *device = mRenderer->getDevice();
-
D3D11_TEXTURE2D_DESC desc;
- desc.Width = mTextureWidth; // Compressed texture size constraints?
- desc.Height = mTextureHeight;
- desc.MipLevels = mipLevels;
- desc.ArraySize = 1;
- desc.Format = mTextureFormat;
- desc.SampleDesc.Count = 1;
+ desc.Width = mTextureWidth; // Compressed texture size constraints?
+ desc.Height = mTextureHeight;
+ desc.MipLevels = mipLevels;
+ desc.ArraySize = 1;
+ desc.Format = mFormatInfo.texFormat;
+ desc.SampleDesc.Count = 1;
desc.SampleDesc.Quality = 0;
- desc.Usage = D3D11_USAGE_DEFAULT;
- desc.BindFlags = getBindFlags();
- desc.CPUAccessFlags = 0;
- desc.MiscFlags = getMiscFlags();
-
- HRESULT result = device->CreateTexture2D(&desc, NULL, outputTexture);
-
- // this can happen from windows TDR
- if (d3d11::isDeviceLostError(result))
- {
- mRenderer->notifyDeviceLost();
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create 2D texture storage, result: 0x%X.", result);
- }
- else if (FAILED(result))
- {
- ASSERT(result == E_OUTOFMEMORY);
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create 2D texture storage, result: 0x%X.", result);
- }
+ desc.Usage = D3D11_USAGE_DEFAULT;
+ desc.BindFlags = getBindFlags();
+ desc.CPUAccessFlags = 0;
+ desc.MiscFlags = getMiscFlags();
- d3d11::SetDebugName(*outputTexture, "TexStorage2D.Texture");
+ ANGLE_TRY(mRenderer->allocateTexture(desc, mFormatInfo, outputTexture));
+ outputTexture->setDebugName("TexStorage2D.Texture");
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error TextureStorage11_2D::getRenderTarget(const gl::ImageIndex &index, RenderTargetD3D **outRT)
+gl::Error TextureStorage11_2D::getRenderTarget(const gl::Context *context,
+ const gl::ImageIndex &index,
+ RenderTargetD3D **outRT)
{
ASSERT(!index.hasLayer());
- int level = index.mipIndex;
+ const int level = index.mipIndex;
ASSERT(level >= 0 && level < getLevelCount());
- // In GL ES 2.0, the application can only render to level zero of the texture (Section 4.4.3 of the GLES 2.0 spec, page 113 of version 2.0.25).
- // Other parts of TextureStorage11_2D could create RTVs on non-zero levels of the texture (e.g. generateMipmap).
- // On Feature Level 9_3, this is unlikely to be useful. The renderer can't create SRVs on the individual levels of the texture,
- // so methods like generateMipmap can't do anything useful with non-zero-level RTVs.
- // Therefore if level > 0 on 9_3 then there's almost certainly something wrong.
- ASSERT(!(mRenderer->getRenderer11DeviceCaps().featureLevel <= D3D_FEATURE_LEVEL_9_3 && level > 0));
-
- if (!mRenderTarget[level])
+ // In GL ES 2.0, the application can only render to level zero of the texture (Section 4.4.3 of
+ // the GLES 2.0 spec, page 113 of version 2.0.25). Other parts of TextureStorage11_2D could
+ // create RTVs on non-zero levels of the texture (e.g. generateMipmap).
+ // On Feature Level 9_3, this is unlikely to be useful. The renderer can't create SRVs on the
+ // individual levels of the texture, so methods like generateMipmap can't do anything useful
+ // with non-zero-level RTVs. Therefore if level > 0 on 9_3 then there's almost certainly
+ // something wrong.
+ ASSERT(
+ !(mRenderer->getRenderer11DeviceCaps().featureLevel <= D3D_FEATURE_LEVEL_9_3 && level > 0));
+ ASSERT(outRT);
+ if (mRenderTarget[level])
{
- ID3D11Resource *texture = NULL;
- gl::Error error = getResource(&texture);
- if (error.isError())
- {
- return error;
- }
-
- ID3D11ShaderResourceView *srv = NULL;
- error = getSRVLevel(level, &srv);
- if (error.isError())
- {
- return error;
- }
-
- if (mUseLevelZeroTexture)
- {
- if (!mLevelZeroRenderTarget)
- {
- ID3D11Device *device = mRenderer->getDevice();
-
- D3D11_RENDER_TARGET_VIEW_DESC rtvDesc;
- rtvDesc.Format = mRenderTargetFormat;
- rtvDesc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE2D;
- rtvDesc.Texture2D.MipSlice = mTopLevel + level;
-
- ID3D11RenderTargetView *rtv;
- HRESULT result = device->CreateRenderTargetView(mLevelZeroTexture, &rtvDesc, &rtv);
+ *outRT = mRenderTarget[level].get();
+ return gl::NoError();
+ }
- if (result == E_OUTOFMEMORY)
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal render target view for texture storage, result: 0x%X.", result);
- }
- ASSERT(SUCCEEDED(result));
+ if (mRenderer->getWorkarounds().zeroMaxLodWorkaround)
+ {
+ ASSERT(index.mipIndex == 0);
+ ANGLE_TRY(useLevelZeroWorkaroundTexture(context, true));
+ }
- mLevelZeroRenderTarget = new TextureRenderTarget11(rtv, mLevelZeroTexture, NULL, mInternalFormat, getLevelWidth(level), getLevelHeight(level), 1, 0);
+ const TextureHelper11 *texture = nullptr;
+ ANGLE_TRY(getResource(context, &texture));
- // RenderTarget will take ownership of these resources
- SafeRelease(rtv);
- }
+ const d3d11::SharedSRV *srv = nullptr;
+ ANGLE_TRY(getSRVLevel(context, level, false, &srv));
- ASSERT(outRT);
- *outRT = mLevelZeroRenderTarget;
- return gl::Error(GL_NO_ERROR);
- }
+ const d3d11::SharedSRV *blitSRV = nullptr;
+ ANGLE_TRY(getSRVLevel(context, level, true, &blitSRV));
- if (mRenderTargetFormat != DXGI_FORMAT_UNKNOWN)
+ if (mUseLevelZeroTexture)
+ {
+ if (!mLevelZeroRenderTarget)
{
- ID3D11Device *device = mRenderer->getDevice();
-
D3D11_RENDER_TARGET_VIEW_DESC rtvDesc;
- rtvDesc.Format = mRenderTargetFormat;
- rtvDesc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE2D;
+ rtvDesc.Format = mFormatInfo.rtvFormat;
+ rtvDesc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE2D;
rtvDesc.Texture2D.MipSlice = mTopLevel + level;
- ID3D11RenderTargetView *rtv;
- HRESULT result = device->CreateRenderTargetView(texture, &rtvDesc, &rtv);
+ d3d11::RenderTargetView rtv;
+ ANGLE_TRY(mRenderer->allocateResource(rtvDesc, mLevelZeroTexture.get(), &rtv));
- ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal render target view for texture storage, result: 0x%X.", result);
- }
-
- mRenderTarget[level] = new TextureRenderTarget11(rtv, texture, srv, mInternalFormat, getLevelWidth(level), getLevelHeight(level), 1, 0);
-
- // RenderTarget will take ownership of these resources
- SafeRelease(rtv);
+ mLevelZeroRenderTarget.reset(new TextureRenderTarget11(
+ std::move(rtv), mLevelZeroTexture, d3d11::SharedSRV(), d3d11::SharedSRV(),
+ mFormatInfo.internalFormat, getFormatSet(), getLevelWidth(level),
+ getLevelHeight(level), 1, 0));
}
- else if (mDepthStencilFormat != DXGI_FORMAT_UNKNOWN)
- {
- ID3D11Device *device = mRenderer->getDevice();
- D3D11_DEPTH_STENCIL_VIEW_DESC dsvDesc;
- dsvDesc.Format = mDepthStencilFormat;
- dsvDesc.ViewDimension = D3D11_DSV_DIMENSION_TEXTURE2D;
- dsvDesc.Texture2D.MipSlice = mTopLevel + level;
- dsvDesc.Flags = 0;
+ *outRT = mLevelZeroRenderTarget.get();
+ return gl::NoError();
+ }
- ID3D11DepthStencilView *dsv;
- HRESULT result = device->CreateDepthStencilView(texture, &dsvDesc, &dsv);
+ if (mFormatInfo.rtvFormat != DXGI_FORMAT_UNKNOWN)
+ {
+ D3D11_RENDER_TARGET_VIEW_DESC rtvDesc;
+ rtvDesc.Format = mFormatInfo.rtvFormat;
+ rtvDesc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE2D;
+ rtvDesc.Texture2D.MipSlice = mTopLevel + level;
- ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY,"Failed to create internal depth stencil view for texture storage, result: 0x%X.", result);
- }
+ d3d11::RenderTargetView rtv;
+ ANGLE_TRY(mRenderer->allocateResource(rtvDesc, texture->get(), &rtv));
- mRenderTarget[level] = new TextureRenderTarget11(dsv, texture, srv, mInternalFormat, getLevelWidth(level), getLevelHeight(level), 1, 0);
+ mRenderTarget[level].reset(new TextureRenderTarget11(
+ std::move(rtv), *texture, *srv, *blitSRV, mFormatInfo.internalFormat, getFormatSet(),
+ getLevelWidth(level), getLevelHeight(level), 1, 0));
- // RenderTarget will take ownership of these resources
- SafeRelease(dsv);
- }
- else
- {
- UNREACHABLE();
- }
+ *outRT = mRenderTarget[level].get();
+ return gl::NoError();
}
- ASSERT(outRT);
- *outRT = mRenderTarget[level];
- return gl::Error(GL_NO_ERROR);
+ ASSERT(mFormatInfo.dsvFormat != DXGI_FORMAT_UNKNOWN);
+
+ D3D11_DEPTH_STENCIL_VIEW_DESC dsvDesc;
+ dsvDesc.Format = mFormatInfo.dsvFormat;
+ dsvDesc.ViewDimension = D3D11_DSV_DIMENSION_TEXTURE2D;
+ dsvDesc.Texture2D.MipSlice = mTopLevel + level;
+ dsvDesc.Flags = 0;
+
+ d3d11::DepthStencilView dsv;
+ ANGLE_TRY(mRenderer->allocateResource(dsvDesc, texture->get(), &dsv));
+
+ mRenderTarget[level].reset(new TextureRenderTarget11(
+ std::move(dsv), *texture, *srv, mFormatInfo.internalFormat, getFormatSet(),
+ getLevelWidth(level), getLevelHeight(level), 1, 0));
+
+ *outRT = mRenderTarget[level].get();
+ return gl::NoError();
}
-gl::Error TextureStorage11_2D::createSRV(int baseLevel, int mipLevels, DXGI_FORMAT format, ID3D11Resource *texture,
- ID3D11ShaderResourceView **outSRV) const
+gl::Error TextureStorage11_2D::createSRV(const gl::Context *context,
+ int baseLevel,
+ int mipLevels,
+ DXGI_FORMAT format,
+ const TextureHelper11 &texture,
+ d3d11::SharedSRV *outSRV)
{
ASSERT(outSRV);
D3D11_SHADER_RESOURCE_VIEW_DESC srvDesc;
- srvDesc.Format = format;
- srvDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2D;
+ srvDesc.Format = format;
+ srvDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2D;
srvDesc.Texture2D.MostDetailedMip = mTopLevel + baseLevel;
- srvDesc.Texture2D.MipLevels = mipLevels;
+ srvDesc.Texture2D.MipLevels = mipLevels;
- ID3D11Resource *srvTexture = texture;
+ const TextureHelper11 *srvTexture = &texture;
if (mRenderer->getWorkarounds().zeroMaxLodWorkaround)
{
ASSERT(mTopLevel == 0);
ASSERT(baseLevel == 0);
- // This code also assumes that the incoming texture equals either mLevelZeroTexture or mTexture.
+ // This code also assumes that the incoming texture equals either mLevelZeroTexture or
+ // mTexture.
if (mipLevels == 1 && mMipLevels > 1)
{
// We must use a SRV on the level-zero-only texture.
- ASSERT(mLevelZeroTexture != NULL && texture == mLevelZeroTexture);
- srvTexture = mLevelZeroTexture;
+ ANGLE_TRY(ensureTextureExists(1));
+ srvTexture = &mLevelZeroTexture;
}
else
{
ASSERT(mipLevels == static_cast<int>(mMipLevels));
- ASSERT(mTexture != NULL && texture == mTexture);
- srvTexture = mTexture;
+ ASSERT(mTexture.valid() && texture == mTexture);
+ srvTexture = &mTexture;
}
}
- ID3D11Device *device = mRenderer->getDevice();
- HRESULT result = device->CreateShaderResourceView(srvTexture, &srvDesc, outSRV);
-
- ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal texture storage SRV, result: 0x%X.", result);
- }
-
- d3d11::SetDebugName(*outSRV, "TexStorage2D.SRV");
+ ANGLE_TRY(mRenderer->allocateResource(srvDesc, srvTexture->get(), outSRV));
+ outSRV->setDebugName("TexStorage2D.SRV");
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error TextureStorage11_2D::getSwizzleTexture(ID3D11Resource **outTexture)
+gl::Error TextureStorage11_2D::getSwizzleTexture(const TextureHelper11 **outTexture)
{
ASSERT(outTexture);
- if (!mSwizzleTexture)
+ if (!mSwizzleTexture.valid())
{
- ID3D11Device *device = mRenderer->getDevice();
+ const auto &format = mFormatInfo.getSwizzleFormat(mRenderer->getRenderer11DeviceCaps());
D3D11_TEXTURE2D_DESC desc;
- desc.Width = mTextureWidth;
- desc.Height = mTextureHeight;
- desc.MipLevels = mMipLevels;
- desc.ArraySize = 1;
- desc.Format = mSwizzleTextureFormat;
- desc.SampleDesc.Count = 1;
+ desc.Width = mTextureWidth;
+ desc.Height = mTextureHeight;
+ desc.MipLevels = mMipLevels;
+ desc.ArraySize = 1;
+ desc.Format = format.texFormat;
+ desc.SampleDesc.Count = 1;
desc.SampleDesc.Quality = 0;
- desc.Usage = D3D11_USAGE_DEFAULT;
- desc.BindFlags = D3D11_BIND_SHADER_RESOURCE | D3D11_BIND_RENDER_TARGET;
- desc.CPUAccessFlags = 0;
- desc.MiscFlags = 0;
-
- HRESULT result = device->CreateTexture2D(&desc, NULL, &mSwizzleTexture);
-
- ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal swizzle texture, result: 0x%X.", result);
- }
+ desc.Usage = D3D11_USAGE_DEFAULT;
+ desc.BindFlags = D3D11_BIND_SHADER_RESOURCE | D3D11_BIND_RENDER_TARGET;
+ desc.CPUAccessFlags = 0;
+ desc.MiscFlags = 0;
- d3d11::SetDebugName(mSwizzleTexture, "TexStorage2D.SwizzleTexture");
+ ANGLE_TRY(mRenderer->allocateTexture(desc, format, &mSwizzleTexture));
+ mSwizzleTexture.setDebugName("TexStorage2D.SwizzleTexture");
}
- *outTexture = mSwizzleTexture;
- return gl::Error(GL_NO_ERROR);
+ *outTexture = &mSwizzleTexture;
+ return gl::NoError();
}
-gl::Error TextureStorage11_2D::getSwizzleRenderTarget(int mipLevel, ID3D11RenderTargetView **outRTV)
+gl::Error TextureStorage11_2D::getSwizzleRenderTarget(int mipLevel,
+ const d3d11::RenderTargetView **outRTV)
{
ASSERT(mipLevel >= 0 && mipLevel < getLevelCount());
ASSERT(outRTV);
- if (!mSwizzleRenderTargets[mipLevel])
+ if (!mSwizzleRenderTargets[mipLevel].valid())
{
- ID3D11Resource *swizzleTexture = NULL;
- gl::Error error = getSwizzleTexture(&swizzleTexture);
- if (error.isError())
- {
- return error;
- }
-
- ID3D11Device *device = mRenderer->getDevice();
+ const TextureHelper11 *swizzleTexture = nullptr;
+ ANGLE_TRY(getSwizzleTexture(&swizzleTexture));
D3D11_RENDER_TARGET_VIEW_DESC rtvDesc;
- rtvDesc.Format = mSwizzleRenderTargetFormat;
- rtvDesc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE2D;
+ rtvDesc.Format =
+ mFormatInfo.getSwizzleFormat(mRenderer->getRenderer11DeviceCaps()).rtvFormat;
+ rtvDesc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE2D;
rtvDesc.Texture2D.MipSlice = mTopLevel + mipLevel;
- HRESULT result = device->CreateRenderTargetView(mSwizzleTexture, &rtvDesc, &mSwizzleRenderTargets[mipLevel]);
-
- ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal swizzle render target view, result: 0x%X.", result);
- }
+ ANGLE_TRY(mRenderer->allocateResource(rtvDesc, mSwizzleTexture.get(),
+ &mSwizzleRenderTargets[mipLevel]));
}
- *outRTV = mSwizzleRenderTargets[mipLevel];
- return gl::Error(GL_NO_ERROR);
+ *outRTV = &mSwizzleRenderTargets[mipLevel];
+ return gl::NoError();
}
-TextureStorage11_EGLImage::TextureStorage11_EGLImage(Renderer11 *renderer, EGLImageD3D *eglImage)
- : TextureStorage11(renderer, D3D11_BIND_RENDER_TARGET | D3D11_BIND_SHADER_RESOURCE, 0),
- mImage(eglImage),
- mCurrentRenderTarget(0),
- mSwizzleTexture(nullptr),
- mSwizzleRenderTargets(gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS, nullptr)
+gl::ErrorOrResult<TextureStorage11::DropStencil> TextureStorage11_2D::ensureDropStencilTexture(
+ const gl::Context *context)
{
- RenderTargetD3D *renderTargetD3D = nullptr;
- mImage->getRenderTarget(&renderTargetD3D);
- RenderTarget11 *renderTarget11 = GetAs<RenderTarget11>(renderTargetD3D);
- mCurrentRenderTarget = reinterpret_cast<uintptr_t>(renderTarget11);
-
- mMipLevels = 1;
- mTextureFormat = renderTarget11->getDXGIFormat();
- mTextureWidth = renderTarget11->getWidth();
- mTextureHeight = renderTarget11->getHeight();
- mTextureDepth = 1;
- mInternalFormat = renderTarget11->getInternalFormat();
-
- ID3D11ShaderResourceView *srv = renderTarget11->getShaderResourceView();
- D3D11_SHADER_RESOURCE_VIEW_DESC srvDesc;
- srv->GetDesc(&srvDesc);
- mShaderResourceFormat = srvDesc.Format;
-
- ID3D11RenderTargetView *rtv = renderTarget11->getRenderTargetView();
- if (rtv != nullptr)
- {
- D3D11_RENDER_TARGET_VIEW_DESC rtvDesc;
- rtv->GetDesc(&rtvDesc);
- mRenderTargetFormat = rtvDesc.Format;
- }
- else
+ if (mDropStencilTexture.valid())
{
- mRenderTargetFormat = DXGI_FORMAT_UNKNOWN;
+ return DropStencil::ALREADY_EXISTS;
}
- ID3D11DepthStencilView *dsv = renderTarget11->getDepthStencilView();
- if (dsv != nullptr)
- {
- D3D11_DEPTH_STENCIL_VIEW_DESC dsvDesc;
- dsv->GetDesc(&dsvDesc);
- mDepthStencilFormat = dsvDesc.Format;
- }
- else
- {
- mDepthStencilFormat = DXGI_FORMAT_UNKNOWN;
- }
+ D3D11_TEXTURE2D_DESC dropDesc = {};
+ dropDesc.ArraySize = 1;
+ dropDesc.BindFlags = D3D11_BIND_SHADER_RESOURCE | D3D11_BIND_DEPTH_STENCIL;
+ dropDesc.CPUAccessFlags = 0;
+ dropDesc.Format = DXGI_FORMAT_R32_TYPELESS;
+ dropDesc.Height = mTextureHeight;
+ dropDesc.MipLevels = mMipLevels;
+ dropDesc.MiscFlags = 0;
+ dropDesc.SampleDesc.Count = 1;
+ dropDesc.SampleDesc.Quality = 0;
+ dropDesc.Usage = D3D11_USAGE_DEFAULT;
+ dropDesc.Width = mTextureWidth;
+
+ const auto &format =
+ d3d11::Format::Get(GL_DEPTH_COMPONENT32F, mRenderer->getRenderer11DeviceCaps());
+ ANGLE_TRY(mRenderer->allocateTexture(dropDesc, format, &mDropStencilTexture));
+ mDropStencilTexture.setDebugName("TexStorage2D.DropStencil");
- const d3d11::DXGIFormat &dxgiFormatInfo = d3d11::GetDXGIFormatInfo(mTextureFormat);
- const d3d11::TextureFormat &formatInfo = d3d11::GetTextureFormatInfo(
- dxgiFormatInfo.internalFormat, mRenderer->getRenderer11DeviceCaps());
- mSwizzleTextureFormat = formatInfo.swizzleTexFormat;
- mSwizzleShaderResourceFormat = formatInfo.swizzleSRVFormat;
- mSwizzleRenderTargetFormat = formatInfo.swizzleRTVFormat;
+ ANGLE_TRY(initDropStencilTexture(context, gl::ImageIndexIterator::Make2D(0, mMipLevels)));
+
+ return DropStencil::CREATED;
}
-TextureStorage11_EGLImage::~TextureStorage11_EGLImage()
+TextureStorage11_External::TextureStorage11_External(
+ Renderer11 *renderer,
+ egl::Stream *stream,
+ const egl::Stream::GLTextureDescription &glDesc)
+ : TextureStorage11(renderer, D3D11_BIND_SHADER_RESOURCE, 0, glDesc.internalFormat)
{
- SafeRelease(mSwizzleTexture);
- for (size_t i = 0; i < mSwizzleRenderTargets.size(); i++)
- {
- SafeRelease(mSwizzleRenderTargets[i]);
- }
+ ASSERT(stream->getProducerType() == egl::Stream::ProducerType::D3D11TextureNV12);
+ StreamProducerNV12 *producer = static_cast<StreamProducerNV12 *>(stream->getImplementation());
+ mTexture.set(producer->getD3DTexture(), mFormatInfo);
+ mSubresourceIndex = producer->getArraySlice();
+ mTexture.get()->AddRef();
+ mMipLevels = 1;
+
+ D3D11_TEXTURE2D_DESC desc;
+ mTexture.getDesc(&desc);
+ mTextureWidth = desc.Width;
+ mTextureHeight = desc.Height;
+ mTextureDepth = 1;
+ mHasKeyedMutex = (desc.MiscFlags & D3D11_RESOURCE_MISC_SHARED_KEYEDMUTEX) != 0;
}
-gl::Error TextureStorage11_EGLImage::getResource(ID3D11Resource **outResource)
+gl::Error TextureStorage11_External::onDestroy(const gl::Context *context)
{
- gl::Error error = checkForUpdatedRenderTarget();
- if (error.isError())
+ if (mHasKeyedMutex)
{
- return error;
+ // If the keyed mutex is released that will unbind it and cause the state cache to become
+ // desynchronized.
+ mRenderer->getStateManager()->invalidateBoundViews();
}
- RenderTarget11 *renderTarget11 = nullptr;
- error = getImageRenderTarget(&renderTarget11);
- if (error.isError())
- {
- return error;
- }
+ return gl::NoError();
+}
+
+TextureStorage11_External::~TextureStorage11_External()
+{
+}
+
+gl::Error TextureStorage11_External::copyToStorage(const gl::Context *context,
+ TextureStorage *destStorage)
+{
+ UNIMPLEMENTED();
+ return gl::NoError();
+}
- *outResource = renderTarget11->getTexture();
- return gl::Error(GL_NO_ERROR);
+void TextureStorage11_External::associateImage(Image11 *image, const gl::ImageIndex &index)
+{
+ ASSERT(index.mipIndex == 0);
+ mAssociatedImage = image;
+}
+
+void TextureStorage11_External::verifyAssociatedImageValid(const gl::ImageIndex &index,
+ Image11 *expectedImage)
+{
+ ASSERT(index.mipIndex == 0 && mAssociatedImage == expectedImage);
}
-gl::Error TextureStorage11_EGLImage::getSRV(const gl::TextureState &textureState,
- ID3D11ShaderResourceView **outSRV)
+void TextureStorage11_External::disassociateImage(const gl::ImageIndex &index,
+ Image11 *expectedImage)
{
- gl::Error error = checkForUpdatedRenderTarget();
- if (error.isError())
+ ASSERT(index.mipIndex == 0);
+ ASSERT(mAssociatedImage == expectedImage);
+ mAssociatedImage = nullptr;
+}
+
+gl::Error TextureStorage11_External::releaseAssociatedImage(const gl::Context *context,
+ const gl::ImageIndex &index,
+ Image11 *incomingImage)
+{
+ ASSERT(index.mipIndex == 0);
+
+ if (mAssociatedImage != nullptr && mAssociatedImage != incomingImage)
{
- return error;
+ mAssociatedImage->verifyAssociatedStorageValid(this);
+
+ ANGLE_TRY(mAssociatedImage->recoverFromAssociatedStorage(context));
}
- return TextureStorage11::getSRV(textureState, outSRV);
+ return gl::NoError();
+}
+
+gl::Error TextureStorage11_External::getResource(const gl::Context *context,
+ const TextureHelper11 **outResource)
+{
+ *outResource = &mTexture;
+ return gl::NoError();
}
-gl::Error TextureStorage11_EGLImage::getMippedResource(ID3D11Resource **)
+gl::Error TextureStorage11_External::getMippedResource(const gl::Context *context,
+ const TextureHelper11 **outResource)
+{
+ *outResource = &mTexture;
+ return gl::NoError();
+}
+
+gl::Error TextureStorage11_External::getRenderTarget(const gl::Context *context,
+ const gl::ImageIndex &index,
+ RenderTargetD3D **outRT)
+{
+ // Render targets are not supported for external textures
+ UNREACHABLE();
+ return gl::InternalError();
+}
+
+gl::Error TextureStorage11_External::createSRV(const gl::Context *context,
+ int baseLevel,
+ int mipLevels,
+ DXGI_FORMAT format,
+ const TextureHelper11 &texture,
+ d3d11::SharedSRV *outSRV)
+{
+ // Since external textures are treates as non-mipmapped textures, we ignore mipmap levels and
+ // use the specified subresource ID the storage was created with.
+ ASSERT(mipLevels == 1);
+ ASSERT(outSRV);
+
+ D3D11_SHADER_RESOURCE_VIEW_DESC srvDesc;
+ srvDesc.Format = format;
+ srvDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2DARRAY;
+ // subresource index is equal to the mip level for 2D textures
+ srvDesc.Texture2DArray.MostDetailedMip = 0;
+ srvDesc.Texture2DArray.MipLevels = 1;
+ srvDesc.Texture2DArray.FirstArraySlice = mSubresourceIndex;
+ srvDesc.Texture2DArray.ArraySize = 1;
+
+ ANGLE_TRY(mRenderer->allocateResource(srvDesc, texture.get(), outSRV));
+ outSRV->setDebugName("TexStorage2D.SRV");
+
+ return gl::NoError();
+}
+
+gl::Error TextureStorage11_External::getSwizzleTexture(const TextureHelper11 **outTexture)
+{
+ UNIMPLEMENTED();
+ return gl::InternalError();
+}
+
+gl::Error TextureStorage11_External::getSwizzleRenderTarget(int mipLevel,
+ const d3d11::RenderTargetView **outRTV)
+{
+ UNIMPLEMENTED();
+ return gl::InternalError();
+}
+
+TextureStorage11_EGLImage::TextureStorage11_EGLImage(Renderer11 *renderer,
+ EGLImageD3D *eglImage,
+ RenderTarget11 *renderTarget11)
+ : TextureStorage11(renderer,
+ D3D11_BIND_RENDER_TARGET | D3D11_BIND_SHADER_RESOURCE,
+ 0,
+ renderTarget11->getInternalFormat()),
+ mImage(eglImage),
+ mCurrentRenderTarget(0),
+ mSwizzleTexture(),
+ mSwizzleRenderTargets(gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS)
+{
+ mCurrentRenderTarget = reinterpret_cast<uintptr_t>(renderTarget11);
+
+ mMipLevels = 1;
+ mTextureWidth = renderTarget11->getWidth();
+ mTextureHeight = renderTarget11->getHeight();
+ mTextureDepth = 1;
+}
+
+TextureStorage11_EGLImage::~TextureStorage11_EGLImage()
+{
+}
+
+gl::Error TextureStorage11_EGLImage::getResource(const gl::Context *context,
+ const TextureHelper11 **outResource)
+{
+ ANGLE_TRY(checkForUpdatedRenderTarget(context));
+
+ RenderTarget11 *renderTarget11 = nullptr;
+ ANGLE_TRY(getImageRenderTarget(context, &renderTarget11));
+ *outResource = &renderTarget11->getTexture();
+ return gl::NoError();
+}
+
+gl::Error TextureStorage11_EGLImage::getSRV(const gl::Context *context,
+ const gl::TextureState &textureState,
+ const d3d11::SharedSRV **outSRV)
+{
+ ANGLE_TRY(checkForUpdatedRenderTarget(context));
+ return TextureStorage11::getSRV(context, textureState, outSRV);
+}
+
+gl::Error TextureStorage11_EGLImage::getMippedResource(const gl::Context *context,
+ const TextureHelper11 **)
{
// This shouldn't be called unless the zero max LOD workaround is active.
// EGL images are unavailable in this configuration.
UNREACHABLE();
- return gl::Error(GL_INVALID_OPERATION);
+ return gl::InternalError();
}
-gl::Error TextureStorage11_EGLImage::getRenderTarget(const gl::ImageIndex &index,
+gl::Error TextureStorage11_EGLImage::getRenderTarget(const gl::Context *context,
+ const gl::ImageIndex &index,
RenderTargetD3D **outRT)
{
ASSERT(!index.hasLayer());
ASSERT(index.mipIndex == 0);
- UNUSED_ASSERTION_VARIABLE(index);
- gl::Error error = checkForUpdatedRenderTarget();
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(checkForUpdatedRenderTarget(context));
- return mImage->getRenderTarget(outRT);
+ return mImage->getRenderTarget(context, outRT);
}
-gl::Error TextureStorage11_EGLImage::copyToStorage(TextureStorage *destStorage)
+gl::Error TextureStorage11_EGLImage::copyToStorage(const gl::Context *context,
+ TextureStorage *destStorage)
{
- ID3D11Resource *sourceResouce = nullptr;
- gl::Error error = getResource(&sourceResouce);
- if (error.isError())
- {
- return error;
- }
+ const TextureHelper11 *sourceResouce = nullptr;
+ ANGLE_TRY(getResource(context, &sourceResouce));
ASSERT(destStorage);
TextureStorage11_2D *dest11 = GetAs<TextureStorage11_2D>(destStorage);
- ID3D11Resource *destResource = nullptr;
- error = dest11->getResource(&destResource);
- if (error.isError())
- {
- return error;
- }
+ const TextureHelper11 *destResource = nullptr;
+ ANGLE_TRY(dest11->getResource(context, &destResource));
ID3D11DeviceContext *immediateContext = mRenderer->getDeviceContext();
- immediateContext->CopyResource(destResource, sourceResouce);
+ immediateContext->CopyResource(destResource->get(), sourceResouce->get());
- dest11->invalidateSwizzleCache();
+ dest11->markDirty();
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
void TextureStorage11_EGLImage::associateImage(Image11 *, const gl::ImageIndex &)
@@ -1508,36 +1530,37 @@ void TextureStorage11_EGLImage::disassociateImage(const gl::ImageIndex &, Image1
{
}
-bool TextureStorage11_EGLImage::isAssociatedImageValid(const gl::ImageIndex &, Image11 *)
+void TextureStorage11_EGLImage::verifyAssociatedImageValid(const gl::ImageIndex &, Image11 *)
{
- return false;
}
-gl::Error TextureStorage11_EGLImage::releaseAssociatedImage(const gl::ImageIndex &, Image11 *)
+gl::Error TextureStorage11_EGLImage::releaseAssociatedImage(const gl::Context *context,
+ const gl::ImageIndex &,
+ Image11 *)
{
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error TextureStorage11_EGLImage::useLevelZeroWorkaroundTexture(bool)
+gl::Error TextureStorage11_EGLImage::useLevelZeroWorkaroundTexture(const gl::Context *context, bool)
{
UNREACHABLE();
- return gl::Error(GL_INVALID_OPERATION);
+ return gl::InternalError();
}
-gl::Error TextureStorage11_EGLImage::getSwizzleTexture(ID3D11Resource **outTexture)
+gl::Error TextureStorage11_EGLImage::getSwizzleTexture(const TextureHelper11 **outTexture)
{
ASSERT(outTexture);
- if (!mSwizzleTexture)
+ if (!mSwizzleTexture.valid())
{
- ID3D11Device *device = mRenderer->getDevice();
+ const auto &format = mFormatInfo.getSwizzleFormat(mRenderer->getRenderer11DeviceCaps());
D3D11_TEXTURE2D_DESC desc;
desc.Width = mTextureWidth;
desc.Height = mTextureHeight;
desc.MipLevels = mMipLevels;
desc.ArraySize = 1;
- desc.Format = mSwizzleTextureFormat;
+ desc.Format = format.texFormat;
desc.SampleDesc.Count = 1;
desc.SampleDesc.Quality = 0;
desc.Usage = D3D11_USAGE_DEFAULT;
@@ -1545,68 +1568,43 @@ gl::Error TextureStorage11_EGLImage::getSwizzleTexture(ID3D11Resource **outTextu
desc.CPUAccessFlags = 0;
desc.MiscFlags = 0;
- HRESULT result = device->CreateTexture2D(&desc, NULL, &mSwizzleTexture);
-
- ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY,
- "Failed to create internal swizzle texture, result: 0x%X.", result);
- }
-
- d3d11::SetDebugName(mSwizzleTexture, "TexStorageEGLImage.SwizzleTexture");
+ ANGLE_TRY(mRenderer->allocateTexture(desc, format, &mSwizzleTexture));
+ mSwizzleTexture.setDebugName("TexStorageEGLImage.SwizzleTexture");
}
- *outTexture = mSwizzleTexture;
- return gl::Error(GL_NO_ERROR);
+ *outTexture = &mSwizzleTexture;
+ return gl::NoError();
}
gl::Error TextureStorage11_EGLImage::getSwizzleRenderTarget(int mipLevel,
- ID3D11RenderTargetView **outRTV)
+ const d3d11::RenderTargetView **outRTV)
{
ASSERT(mipLevel >= 0 && mipLevel < getLevelCount());
ASSERT(outRTV);
- if (!mSwizzleRenderTargets[mipLevel])
+ if (!mSwizzleRenderTargets[mipLevel].valid())
{
- ID3D11Resource *swizzleTexture = NULL;
- gl::Error error = getSwizzleTexture(&swizzleTexture);
- if (error.isError())
- {
- return error;
- }
-
- ID3D11Device *device = mRenderer->getDevice();
+ const TextureHelper11 *swizzleTexture = nullptr;
+ ANGLE_TRY(getSwizzleTexture(&swizzleTexture));
D3D11_RENDER_TARGET_VIEW_DESC rtvDesc;
- rtvDesc.Format = mSwizzleRenderTargetFormat;
+ rtvDesc.Format =
+ mFormatInfo.getSwizzleFormat(mRenderer->getRenderer11DeviceCaps()).rtvFormat;
rtvDesc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE2D;
rtvDesc.Texture2D.MipSlice = mTopLevel + mipLevel;
- HRESULT result = device->CreateRenderTargetView(mSwizzleTexture, &rtvDesc,
- &mSwizzleRenderTargets[mipLevel]);
-
- ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY,
- "Failed to create internal swizzle render target view, result: 0x%X.",
- result);
- }
+ ANGLE_TRY(mRenderer->allocateResource(rtvDesc, mSwizzleTexture.get(),
+ &mSwizzleRenderTargets[mipLevel]));
}
- *outRTV = mSwizzleRenderTargets[mipLevel];
- return gl::Error(GL_NO_ERROR);
+ *outRTV = &mSwizzleRenderTargets[mipLevel];
+ return gl::NoError();
}
-gl::Error TextureStorage11_EGLImage::checkForUpdatedRenderTarget()
+gl::Error TextureStorage11_EGLImage::checkForUpdatedRenderTarget(const gl::Context *context)
{
RenderTarget11 *renderTarget11 = nullptr;
- gl::Error error = getImageRenderTarget(&renderTarget11);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(getImageRenderTarget(context, &renderTarget11));
if (mCurrentRenderTarget != reinterpret_cast<uintptr_t>(renderTarget11))
{
@@ -1614,14 +1612,15 @@ gl::Error TextureStorage11_EGLImage::checkForUpdatedRenderTarget()
mCurrentRenderTarget = reinterpret_cast<uintptr_t>(renderTarget11);
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error TextureStorage11_EGLImage::createSRV(int baseLevel,
+gl::Error TextureStorage11_EGLImage::createSRV(const gl::Context *context,
+ int baseLevel,
int mipLevels,
DXGI_FORMAT format,
- ID3D11Resource *texture,
- ID3D11ShaderResourceView **outSRV) const
+ const TextureHelper11 &texture,
+ d3d11::SharedSRV *outSRV)
{
ASSERT(baseLevel == 0);
ASSERT(mipLevels == 1);
@@ -1637,163 +1636,129 @@ gl::Error TextureStorage11_EGLImage::createSRV(int baseLevel,
srvDesc.Texture2D.MostDetailedMip = mTopLevel + baseLevel;
srvDesc.Texture2D.MipLevels = mipLevels;
- ID3D11Device *device = mRenderer->getDevice();
- HRESULT result = device->CreateShaderResourceView(texture, &srvDesc, outSRV);
-
- ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY,
- "Failed to create internal texture storage SRV, result: 0x%X.",
- result);
- }
-
- d3d11::SetDebugName(*outSRV, "TexStorageEGLImage.SRV");
+ ANGLE_TRY(mRenderer->allocateResource(srvDesc, texture.get(), outSRV));
+ outSRV->setDebugName("TexStorageEGLImage.SRV");
}
else
{
RenderTarget11 *renderTarget = nullptr;
- gl::Error error = getImageRenderTarget(&renderTarget);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(getImageRenderTarget(context, &renderTarget));
ASSERT(texture == renderTarget->getTexture());
- *outSRV = renderTarget->getShaderResourceView();
- (*outSRV)->AddRef();
+ *outSRV = renderTarget->getShaderResourceView().makeCopy();
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error TextureStorage11_EGLImage::getImageRenderTarget(RenderTarget11 **outRT) const
+gl::Error TextureStorage11_EGLImage::getImageRenderTarget(const gl::Context *context,
+ RenderTarget11 **outRT) const
{
RenderTargetD3D *renderTargetD3D = nullptr;
- gl::Error error = mImage->getRenderTarget(&renderTargetD3D);
- if (error.isError())
- {
- return error;
- }
-
+ ANGLE_TRY(mImage->getRenderTarget(context, &renderTargetD3D));
*outRT = GetAs<RenderTarget11>(renderTargetD3D);
- return gl::Error(GL_NO_ERROR);
-}
-
-TextureStorage11_Cube::TextureStorage11_Cube(Renderer11 *renderer, GLenum internalformat, bool renderTarget, int size, int levels, bool hintLevelZeroOnly)
- : TextureStorage11(renderer,
- GetTextureBindFlags(internalformat, renderer->getRenderer11DeviceCaps(), renderTarget),
- GetTextureMiscFlags(internalformat, renderer->getRenderer11DeviceCaps(), renderTarget, levels))
+ return gl::NoError();
+}
+
+TextureStorage11_Cube::TextureStorage11_Cube(Renderer11 *renderer,
+ GLenum internalformat,
+ bool renderTarget,
+ int size,
+ int levels,
+ bool hintLevelZeroOnly)
+ : TextureStorage11(
+ renderer,
+ GetTextureBindFlags(internalformat, renderer->getRenderer11DeviceCaps(), renderTarget),
+ GetTextureMiscFlags(internalformat,
+ renderer->getRenderer11DeviceCaps(),
+ renderTarget,
+ levels),
+ internalformat),
+ mTexture(),
+ mLevelZeroTexture(),
+ mUseLevelZeroTexture(hintLevelZeroOnly && levels > 1),
+ mSwizzleTexture()
{
- mTexture = NULL;
- mSwizzleTexture = NULL;
-
for (unsigned int level = 0; level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS; level++)
{
- mSwizzleRenderTargets[level] = NULL;
- for (unsigned int face = 0; face < CUBE_FACE_COUNT; face++)
+ for (unsigned int face = 0; face < gl::CUBE_FACE_COUNT; face++)
{
- mAssociatedImages[face][level] = NULL;
- mRenderTarget[face][level] = NULL;
+ mAssociatedImages[face][level] = nullptr;
+ mRenderTarget[face][level] = nullptr;
}
}
- mLevelZeroTexture = NULL;
- mUseLevelZeroTexture = false;
-
- for (unsigned int face = 0; face < CUBE_FACE_COUNT; face++)
+ for (unsigned int face = 0; face < gl::CUBE_FACE_COUNT; face++)
{
- mLevelZeroRenderTarget[face] = NULL;
+ mLevelZeroRenderTarget[face] = nullptr;
}
- mInternalFormat = internalformat;
-
- const d3d11::TextureFormat &formatInfo = d3d11::GetTextureFormatInfo(internalformat, renderer->getRenderer11DeviceCaps());
- mTextureFormat = formatInfo.texFormat;
- mShaderResourceFormat = formatInfo.srvFormat;
- mDepthStencilFormat = formatInfo.dsvFormat;
- mRenderTargetFormat = formatInfo.rtvFormat;
- mSwizzleTextureFormat = formatInfo.swizzleTexFormat;
- mSwizzleShaderResourceFormat = formatInfo.swizzleSRVFormat;
- mSwizzleRenderTargetFormat = formatInfo.swizzleRTVFormat;
-
// adjust size if needed for compressed textures
int height = size;
- d3d11::MakeValidSize(false, mTextureFormat, &size, &height, &mTopLevel);
+ d3d11::MakeValidSize(false, mFormatInfo.texFormat, &size, &height, &mTopLevel);
- mMipLevels = mTopLevel + levels;
- mTextureWidth = size;
+ mMipLevels = mTopLevel + levels;
+ mTextureWidth = size;
mTextureHeight = size;
- mTextureDepth = 1;
+ mTextureDepth = 1;
- if (hintLevelZeroOnly && levels > 1)
- {
- //The LevelZeroOnly hint should only be true if the zero max LOD workaround is active.
- ASSERT(mRenderer->getWorkarounds().zeroMaxLodWorkaround);
- mUseLevelZeroTexture = true;
- }
+ // The LevelZeroOnly hint should only be true if the zero max LOD workaround is active.
+ ASSERT(!mUseLevelZeroTexture || mRenderer->getWorkarounds().zeroMaxLodWorkaround);
}
-TextureStorage11_Cube::~TextureStorage11_Cube()
+gl::Error TextureStorage11_Cube::onDestroy(const gl::Context *context)
{
for (unsigned int level = 0; level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS; level++)
{
- for (unsigned int face = 0; face < CUBE_FACE_COUNT; face++)
+ for (unsigned int face = 0; face < gl::CUBE_FACE_COUNT; face++)
{
- if (mAssociatedImages[face][level] != NULL)
+ if (mAssociatedImages[face][level] != nullptr)
{
- bool imageAssociationCorrect = mAssociatedImages[face][level]->isAssociatedStorageValid(this);
- ASSERT(imageAssociationCorrect);
-
- if (imageAssociationCorrect)
- {
- // We must let the Images recover their data before we delete it from the TextureStorage.
- mAssociatedImages[face][level]->recoverFromAssociatedStorage();
- }
+ mAssociatedImages[face][level]->verifyAssociatedStorageValid(this);
+
+ // We must let the Images recover their data before we delete it from the
+ // TextureStorage.
+ ANGLE_TRY(mAssociatedImages[face][level]->recoverFromAssociatedStorage(context));
}
}
}
- SafeRelease(mTexture);
- SafeRelease(mSwizzleTexture);
- SafeRelease(mLevelZeroTexture);
-
- for (unsigned int face = 0; face < CUBE_FACE_COUNT; face++)
+ for (auto &faceRenderTargets : mRenderTarget)
{
- SafeDelete(mLevelZeroRenderTarget[face]);
+ InvalidateRenderTargetContainer(context, &faceRenderTargets);
}
+ InvalidateRenderTargetContainer(context, &mLevelZeroRenderTarget);
- for (unsigned int level = 0; level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS; level++)
- {
- SafeRelease(mSwizzleRenderTargets[level]);
- for (unsigned int face = 0; face < CUBE_FACE_COUNT; face++)
- {
- SafeDelete(mRenderTarget[face][level]);
- }
- }
+ return gl::NoError();
+}
+
+TextureStorage11_Cube::~TextureStorage11_Cube()
+{
}
UINT TextureStorage11_Cube::getSubresourceIndex(const gl::ImageIndex &index) const
{
- if (mRenderer->getWorkarounds().zeroMaxLodWorkaround && mUseLevelZeroTexture && index.mipIndex == 0)
+ if (mRenderer->getWorkarounds().zeroMaxLodWorkaround && mUseLevelZeroTexture &&
+ index.mipIndex == 0)
{
- UINT arraySlice = static_cast<UINT>(index.hasLayer() ? index.layerIndex : 0);
+ UINT arraySlice = static_cast<UINT>(index.hasLayer() ? index.layerIndex : 0);
UINT subresource = D3D11CalcSubresource(0, arraySlice, 1);
ASSERT(subresource != std::numeric_limits<UINT>::max());
return subresource;
}
else
{
- UINT mipSlice = static_cast<UINT>(index.mipIndex + mTopLevel);
- UINT arraySlice = static_cast<UINT>(index.hasLayer() ? index.layerIndex : 0);
+ UINT mipSlice = static_cast<UINT>(index.mipIndex + mTopLevel);
+ UINT arraySlice = static_cast<UINT>(index.hasLayer() ? index.layerIndex : 0);
UINT subresource = D3D11CalcSubresource(mipSlice, arraySlice, mMipLevels);
ASSERT(subresource != std::numeric_limits<UINT>::max());
return subresource;
}
}
-gl::Error TextureStorage11_Cube::copyToStorage(TextureStorage *destStorage)
+gl::Error TextureStorage11_Cube::copyToStorage(const gl::Context *context,
+ TextureStorage *destStorage)
{
ASSERT(destStorage);
@@ -1803,87 +1768,63 @@ gl::Error TextureStorage11_Cube::copyToStorage(TextureStorage *destStorage)
{
ID3D11DeviceContext *immediateContext = mRenderer->getDeviceContext();
- // If either mTexture or mLevelZeroTexture exist, then we need to copy them into the corresponding textures in destStorage.
- if (mTexture)
+ // If either mTexture or mLevelZeroTexture exist, then we need to copy them into the
+ // corresponding textures in destStorage.
+ if (mTexture.valid())
{
- gl::Error error = dest11->useLevelZeroWorkaroundTexture(false);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(dest11->useLevelZeroWorkaroundTexture(context, false));
- ID3D11Resource *destResource = NULL;
- error = dest11->getResource(&destResource);
- if (error.isError())
- {
- return error;
- }
+ const TextureHelper11 *destResource = nullptr;
+ ANGLE_TRY(dest11->getResource(context, &destResource));
- immediateContext->CopyResource(destResource, mTexture);
+ immediateContext->CopyResource(destResource->get(), mTexture.get());
}
- if (mLevelZeroTexture)
+ if (mLevelZeroTexture.valid())
{
- gl::Error error = dest11->useLevelZeroWorkaroundTexture(true);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(dest11->useLevelZeroWorkaroundTexture(context, true));
- ID3D11Resource *destResource = NULL;
- error = dest11->getResource(&destResource);
- if (error.isError())
- {
- return error;
- }
+ const TextureHelper11 *destResource = nullptr;
+ ANGLE_TRY(dest11->getResource(context, &destResource));
- immediateContext->CopyResource(destResource, mLevelZeroTexture);
+ immediateContext->CopyResource(destResource->get(), mLevelZeroTexture.get());
}
}
else
{
- ID3D11Resource *sourceResouce = NULL;
- gl::Error error = getResource(&sourceResouce);
- if (error.isError())
- {
- return error;
- }
+ const TextureHelper11 *sourceResouce = nullptr;
+ ANGLE_TRY(getResource(context, &sourceResouce));
- ID3D11Resource *destResource = NULL;
- error = dest11->getResource(&destResource);
- if (error.isError())
- {
- return error;
- }
+ const TextureHelper11 *destResource = nullptr;
+ ANGLE_TRY(dest11->getResource(context, &destResource));
ID3D11DeviceContext *immediateContext = mRenderer->getDeviceContext();
- immediateContext->CopyResource(destResource, sourceResouce);
+ immediateContext->CopyResource(destResource->get(), sourceResouce->get());
}
- dest11->invalidateSwizzleCache();
+ dest11->markDirty();
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error TextureStorage11_Cube::useLevelZeroWorkaroundTexture(bool useLevelZeroTexture)
+gl::Error TextureStorage11_Cube::useLevelZeroWorkaroundTexture(const gl::Context *context,
+ bool useLevelZeroTexture)
{
if (useLevelZeroTexture && mMipLevels > 1)
{
- if (!mUseLevelZeroTexture && mTexture)
+ if (!mUseLevelZeroTexture && mTexture.valid())
{
- gl::Error error = ensureTextureExists(1);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(ensureTextureExists(1));
// Pull data back from the mipped texture if necessary.
- ASSERT(mLevelZeroTexture);
- ID3D11DeviceContext *context = mRenderer->getDeviceContext();
+ ASSERT(mLevelZeroTexture.valid());
+ ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
for (int face = 0; face < 6; face++)
{
- context->CopySubresourceRegion(mLevelZeroTexture, D3D11CalcSubresource(0, face, 1), 0, 0, 0, mTexture, face * mMipLevels, NULL);
+ deviceContext->CopySubresourceRegion(mLevelZeroTexture.get(),
+ D3D11CalcSubresource(0, face, 1), 0, 0, 0,
+ mTexture.get(), face * mMipLevels, nullptr);
}
}
@@ -1891,346 +1832,286 @@ gl::Error TextureStorage11_Cube::useLevelZeroWorkaroundTexture(bool useLevelZero
}
else
{
- if (mUseLevelZeroTexture && mLevelZeroTexture)
+ if (mUseLevelZeroTexture && mLevelZeroTexture.valid())
{
- gl::Error error = ensureTextureExists(mMipLevels);
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(ensureTextureExists(mMipLevels));
// Pull data back from the level zero texture if necessary.
- ASSERT(mTexture);
- ID3D11DeviceContext *context = mRenderer->getDeviceContext();
+ ASSERT(mTexture.valid());
+ ID3D11DeviceContext *deviceContext = mRenderer->getDeviceContext();
for (int face = 0; face < 6; face++)
{
- context->CopySubresourceRegion(mTexture, D3D11CalcSubresource(0, face, mMipLevels), 0, 0, 0, mLevelZeroTexture, face, NULL);
+ deviceContext->CopySubresourceRegion(mTexture.get(),
+ D3D11CalcSubresource(0, face, mMipLevels), 0,
+ 0, 0, mLevelZeroTexture.get(), face, nullptr);
}
}
mUseLevelZeroTexture = false;
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-void TextureStorage11_Cube::associateImage(Image11* image, const gl::ImageIndex &index)
+void TextureStorage11_Cube::associateImage(Image11 *image, const gl::ImageIndex &index)
{
- GLint level = index.mipIndex;
- GLint layerTarget = index.layerIndex;
+ const GLint level = index.mipIndex;
+ const GLint layerTarget = index.layerIndex;
ASSERT(0 <= level && level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS);
- ASSERT(0 <= layerTarget && layerTarget < CUBE_FACE_COUNT);
+ ASSERT(0 <= layerTarget && layerTarget < static_cast<GLint>(gl::CUBE_FACE_COUNT));
if (0 <= level && level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS)
{
- if (0 <= layerTarget && layerTarget < CUBE_FACE_COUNT)
+ if (0 <= layerTarget && layerTarget < static_cast<GLint>(gl::CUBE_FACE_COUNT))
{
mAssociatedImages[layerTarget][level] = image;
}
}
}
-bool TextureStorage11_Cube::isAssociatedImageValid(const gl::ImageIndex &index, Image11* expectedImage)
+void TextureStorage11_Cube::verifyAssociatedImageValid(const gl::ImageIndex &index,
+ Image11 *expectedImage)
{
- GLint level = index.mipIndex;
- GLint layerTarget = index.layerIndex;
-
- if (0 <= level && level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS)
- {
- if (0 <= layerTarget && layerTarget < CUBE_FACE_COUNT)
- {
- // This validation check should never return false. It means the Image/TextureStorage association is broken.
- bool retValue = (mAssociatedImages[layerTarget][level] == expectedImage);
- ASSERT(retValue);
- return retValue;
- }
- }
+ const GLint level = index.mipIndex;
+ const GLint layerTarget = index.layerIndex;
- return false;
+ ASSERT(0 <= level && level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS);
+ ASSERT(0 <= layerTarget && layerTarget < static_cast<GLint>(gl::CUBE_FACE_COUNT));
+ // This validation check should never return false. It means the Image/TextureStorage
+ // association is broken.
+ ASSERT(mAssociatedImages[layerTarget][level] == expectedImage);
}
// disassociateImage allows an Image to end its association with a Storage.
-void TextureStorage11_Cube::disassociateImage(const gl::ImageIndex &index, Image11* expectedImage)
+void TextureStorage11_Cube::disassociateImage(const gl::ImageIndex &index, Image11 *expectedImage)
{
- GLint level = index.mipIndex;
- GLint layerTarget = index.layerIndex;
+ const GLint level = index.mipIndex;
+ const GLint layerTarget = index.layerIndex;
ASSERT(0 <= level && level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS);
- ASSERT(0 <= layerTarget && layerTarget < CUBE_FACE_COUNT);
-
- if (0 <= level && level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS)
- {
- if (0 <= layerTarget && layerTarget < CUBE_FACE_COUNT)
- {
- ASSERT(mAssociatedImages[layerTarget][level] == expectedImage);
-
- if (mAssociatedImages[layerTarget][level] == expectedImage)
- {
- mAssociatedImages[layerTarget][level] = NULL;
- }
- }
- }
+ ASSERT(0 <= layerTarget && layerTarget < static_cast<GLint>(gl::CUBE_FACE_COUNT));
+ ASSERT(mAssociatedImages[layerTarget][level] == expectedImage);
+ mAssociatedImages[layerTarget][level] = nullptr;
}
-// releaseAssociatedImage prepares the Storage for a new Image association. It lets the old Image recover its data before ending the association.
-gl::Error TextureStorage11_Cube::releaseAssociatedImage(const gl::ImageIndex &index, Image11* incomingImage)
+// releaseAssociatedImage prepares the Storage for a new Image association. It lets the old Image
+// recover its data before ending the association.
+gl::Error TextureStorage11_Cube::releaseAssociatedImage(const gl::Context *context,
+ const gl::ImageIndex &index,
+ Image11 *incomingImage)
{
- GLint level = index.mipIndex;
- GLint layerTarget = index.layerIndex;
+ const GLint level = index.mipIndex;
+ const GLint layerTarget = index.layerIndex;
ASSERT(0 <= level && level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS);
- ASSERT(0 <= layerTarget && layerTarget < CUBE_FACE_COUNT);
+ ASSERT(0 <= layerTarget && layerTarget < static_cast<GLint>(gl::CUBE_FACE_COUNT));
if ((0 <= level && level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS))
{
- if (0 <= layerTarget && layerTarget < CUBE_FACE_COUNT)
+ if (0 <= layerTarget && layerTarget < static_cast<GLint>(gl::CUBE_FACE_COUNT))
{
// No need to let the old Image recover its data, if it is also the incoming Image.
- if (mAssociatedImages[layerTarget][level] != NULL && mAssociatedImages[layerTarget][level] != incomingImage)
+ if (mAssociatedImages[layerTarget][level] != nullptr &&
+ mAssociatedImages[layerTarget][level] != incomingImage)
{
- // Ensure that the Image is still associated with this TextureStorage. This should be true.
- bool imageAssociationCorrect = mAssociatedImages[layerTarget][level]->isAssociatedStorageValid(this);
- ASSERT(imageAssociationCorrect);
-
- if (imageAssociationCorrect)
- {
- // Force the image to recover from storage before its data is overwritten.
- // This will reset mAssociatedImages[level] to NULL too.
- gl::Error error = mAssociatedImages[layerTarget][level]->recoverFromAssociatedStorage();
- if (error.isError())
- {
- return error;
- }
- }
+ // Ensure that the Image is still associated with this TextureStorage.
+ mAssociatedImages[layerTarget][level]->verifyAssociatedStorageValid(this);
+
+ // Force the image to recover from storage before its data is overwritten.
+ // This will reset mAssociatedImages[level] to nullptr too.
+ ANGLE_TRY(
+ mAssociatedImages[layerTarget][level]->recoverFromAssociatedStorage(context));
}
}
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error TextureStorage11_Cube::getResource(ID3D11Resource **outResource)
+gl::Error TextureStorage11_Cube::getResource(const gl::Context *context,
+ const TextureHelper11 **outResource)
{
if (mUseLevelZeroTexture && mMipLevels > 1)
{
- gl::Error error = ensureTextureExists(1);
- if (error.isError())
- {
- return error;
- }
-
- *outResource = mLevelZeroTexture;
- return gl::Error(GL_NO_ERROR);
+ ANGLE_TRY(ensureTextureExists(1));
+ *outResource = &mLevelZeroTexture;
+ return gl::NoError();
}
else
{
- gl::Error error = ensureTextureExists(mMipLevels);
- if (error.isError())
- {
- return error;
- }
-
- *outResource = mTexture;
- return gl::Error(GL_NO_ERROR);
+ ANGLE_TRY(ensureTextureExists(mMipLevels));
+ *outResource = &mTexture;
+ return gl::NoError();
}
}
-gl::Error TextureStorage11_Cube::getMippedResource(ID3D11Resource **outResource)
+gl::Error TextureStorage11_Cube::getMippedResource(const gl::Context *context,
+ const TextureHelper11 **outResource)
{
// This shouldn't be called unless the zero max LOD workaround is active.
ASSERT(mRenderer->getWorkarounds().zeroMaxLodWorkaround);
- gl::Error error = ensureTextureExists(mMipLevels);
- if (error.isError())
- {
- return error;
- }
-
- *outResource = mTexture;
- return gl::Error(GL_NO_ERROR);
+ ANGLE_TRY(ensureTextureExists(mMipLevels));
+ *outResource = &mTexture;
+ return gl::NoError();
}
gl::Error TextureStorage11_Cube::ensureTextureExists(int mipLevels)
{
// If mMipLevels = 1 then always use mTexture rather than mLevelZeroTexture.
- bool useLevelZeroTexture = mRenderer->getWorkarounds().zeroMaxLodWorkaround ? (mipLevels == 1) && (mMipLevels > 1) : false;
- ID3D11Texture2D **outputTexture = useLevelZeroTexture ? &mLevelZeroTexture : &mTexture;
+ bool useLevelZeroTexture = mRenderer->getWorkarounds().zeroMaxLodWorkaround
+ ? (mipLevels == 1) && (mMipLevels > 1)
+ : false;
+ TextureHelper11 *outputTexture = useLevelZeroTexture ? &mLevelZeroTexture : &mTexture;
// if the size is not positive this should be treated as an incomplete texture
// we handle that here by skipping the d3d texture creation
- if (*outputTexture == NULL && mTextureWidth > 0 && mTextureHeight > 0)
+ if (!outputTexture->valid() && mTextureWidth > 0 && mTextureHeight > 0)
{
ASSERT(mMipLevels > 0);
- ID3D11Device *device = mRenderer->getDevice();
-
D3D11_TEXTURE2D_DESC desc;
- desc.Width = mTextureWidth;
- desc.Height = mTextureHeight;
- desc.MipLevels = mipLevels;
- desc.ArraySize = CUBE_FACE_COUNT;
- desc.Format = mTextureFormat;
- desc.SampleDesc.Count = 1;
+ desc.Width = mTextureWidth;
+ desc.Height = mTextureHeight;
+ desc.MipLevels = mipLevels;
+ desc.ArraySize = gl::CUBE_FACE_COUNT;
+ desc.Format = mFormatInfo.texFormat;
+ desc.SampleDesc.Count = 1;
desc.SampleDesc.Quality = 0;
- desc.Usage = D3D11_USAGE_DEFAULT;
- desc.BindFlags = getBindFlags();
- desc.CPUAccessFlags = 0;
- desc.MiscFlags = D3D11_RESOURCE_MISC_TEXTURECUBE | getMiscFlags();
+ desc.Usage = D3D11_USAGE_DEFAULT;
+ desc.BindFlags = getBindFlags();
+ desc.CPUAccessFlags = 0;
+ desc.MiscFlags = D3D11_RESOURCE_MISC_TEXTURECUBE | getMiscFlags();
- HRESULT result = device->CreateTexture2D(&desc, NULL, outputTexture);
+ ANGLE_TRY(mRenderer->allocateTexture(desc, mFormatInfo, outputTexture));
+ outputTexture->setDebugName("TexStorageCube.Texture");
+ }
- // this can happen from windows TDR
- if (d3d11::isDeviceLostError(result))
- {
- mRenderer->notifyDeviceLost();
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create cube texture storage, result: 0x%X.", result);
- }
- else if (FAILED(result))
- {
- ASSERT(result == E_OUTOFMEMORY);
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create cube texture storage, result: 0x%X.", result);
- }
+ return gl::NoError();
+}
+
+gl::Error TextureStorage11_Cube::createRenderTargetSRV(const TextureHelper11 &texture,
+ const gl::ImageIndex &index,
+ DXGI_FORMAT resourceFormat,
+ d3d11::SharedSRV *srv) const
+{
+ D3D11_SHADER_RESOURCE_VIEW_DESC srvDesc;
+ srvDesc.Format = resourceFormat;
+ srvDesc.Texture2DArray.MostDetailedMip = mTopLevel + index.mipIndex;
+ srvDesc.Texture2DArray.MipLevels = 1;
+ srvDesc.Texture2DArray.FirstArraySlice = index.layerIndex;
+ srvDesc.Texture2DArray.ArraySize = 1;
- d3d11::SetDebugName(*outputTexture, "TexStorageCube.Texture");
+ if (mRenderer->getRenderer11DeviceCaps().featureLevel <= D3D_FEATURE_LEVEL_10_0)
+ {
+ srvDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURECUBE;
+ }
+ else
+ {
+ // Will be used with Texture2D sampler, not TextureCube
+ srvDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2DARRAY;
}
- return gl::Error(GL_NO_ERROR);
+ ANGLE_TRY(mRenderer->allocateResource(srvDesc, texture.get(), srv));
+ return gl::NoError();
}
-gl::Error TextureStorage11_Cube::getRenderTarget(const gl::ImageIndex &index, RenderTargetD3D **outRT)
+gl::Error TextureStorage11_Cube::getRenderTarget(const gl::Context *context,
+ const gl::ImageIndex &index,
+ RenderTargetD3D **outRT)
{
- int faceIndex = index.layerIndex;
- int level = index.mipIndex;
+ const int faceIndex = index.layerIndex;
+ const int level = index.mipIndex;
ASSERT(level >= 0 && level < getLevelCount());
- ASSERT(faceIndex >= 0 && faceIndex < CUBE_FACE_COUNT);
+ ASSERT(faceIndex >= 0 && faceIndex < static_cast<GLint>(gl::CUBE_FACE_COUNT));
if (!mRenderTarget[faceIndex][level])
{
- ID3D11Device *device = mRenderer->getDevice();
- HRESULT result;
-
- ID3D11Resource *texture = NULL;
- gl::Error error = getResource(&texture);
- if (error.isError())
+ if (mRenderer->getWorkarounds().zeroMaxLodWorkaround)
{
- return error;
+ ASSERT(index.mipIndex == 0);
+ ANGLE_TRY(useLevelZeroWorkaroundTexture(context, true));
}
+ const TextureHelper11 *texture = nullptr;
+ ANGLE_TRY(getResource(context, &texture));
+
if (mUseLevelZeroTexture)
{
if (!mLevelZeroRenderTarget[faceIndex])
{
D3D11_RENDER_TARGET_VIEW_DESC rtvDesc;
- rtvDesc.Format = mRenderTargetFormat;
- rtvDesc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE2DARRAY;
- rtvDesc.Texture2DArray.MipSlice = mTopLevel + level;
+ rtvDesc.Format = mFormatInfo.rtvFormat;
+ rtvDesc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE2DARRAY;
+ rtvDesc.Texture2DArray.MipSlice = mTopLevel + level;
rtvDesc.Texture2DArray.FirstArraySlice = faceIndex;
- rtvDesc.Texture2DArray.ArraySize = 1;
-
- ID3D11RenderTargetView *rtv;
- result = device->CreateRenderTargetView(mLevelZeroTexture, &rtvDesc, &rtv);
+ rtvDesc.Texture2DArray.ArraySize = 1;
- if (result == E_OUTOFMEMORY)
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal render target view for texture storage, result: 0x%X.", result);
- }
- ASSERT(SUCCEEDED(result));
+ d3d11::RenderTargetView rtv;
+ ANGLE_TRY(mRenderer->allocateResource(rtvDesc, mLevelZeroTexture.get(), &rtv));
- mLevelZeroRenderTarget[faceIndex] = new TextureRenderTarget11(rtv, mLevelZeroTexture, NULL, mInternalFormat, getLevelWidth(level), getLevelHeight(level), 1, 0);
-
- // RenderTarget will take ownership of these resources
- SafeRelease(rtv);
+ mLevelZeroRenderTarget[faceIndex].reset(new TextureRenderTarget11(
+ std::move(rtv), mLevelZeroTexture, d3d11::SharedSRV(), d3d11::SharedSRV(),
+ mFormatInfo.internalFormat, getFormatSet(), getLevelWidth(level),
+ getLevelHeight(level), 1, 0));
}
ASSERT(outRT);
- *outRT = mLevelZeroRenderTarget[faceIndex];
- return gl::Error(GL_NO_ERROR);
+ *outRT = mLevelZeroRenderTarget[faceIndex].get();
+ return gl::NoError();
}
- D3D11_SHADER_RESOURCE_VIEW_DESC srvDesc;
- srvDesc.Format = mShaderResourceFormat;
- srvDesc.Texture2DArray.MostDetailedMip = mTopLevel + level;
- srvDesc.Texture2DArray.MipLevels = 1;
- srvDesc.Texture2DArray.FirstArraySlice = faceIndex;
- srvDesc.Texture2DArray.ArraySize = 1;
-
- if (mRenderer->getRenderer11DeviceCaps().featureLevel <= D3D_FEATURE_LEVEL_9_3)
+ d3d11::SharedSRV srv;
+ ANGLE_TRY(createRenderTargetSRV(*texture, index, mFormatInfo.srvFormat, &srv));
+ d3d11::SharedSRV blitSRV;
+ if (mFormatInfo.blitSRVFormat != mFormatInfo.srvFormat)
{
- srvDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURECUBE;
+ ANGLE_TRY(createRenderTargetSRV(*texture, index, mFormatInfo.blitSRVFormat, &blitSRV));
}
else
{
- srvDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2DARRAY; // Will be used with Texture2D sampler, not TextureCube
+ blitSRV = srv.makeCopy();
}
- ID3D11ShaderResourceView *srv;
- result = device->CreateShaderResourceView(texture, &srvDesc, &srv);
+ srv.setDebugName("TexStorageCube.RenderTargetSRV");
- ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal shader resource view for texture storage, result: 0x%X.", result);
- }
-
- d3d11::SetDebugName(srv, "TexStorageCube.RenderTargetSRV");
-
- if (mRenderTargetFormat != DXGI_FORMAT_UNKNOWN)
+ if (mFormatInfo.rtvFormat != DXGI_FORMAT_UNKNOWN)
{
D3D11_RENDER_TARGET_VIEW_DESC rtvDesc;
- rtvDesc.Format = mRenderTargetFormat;
- rtvDesc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE2DARRAY;
- rtvDesc.Texture2DArray.MipSlice = mTopLevel + level;
+ rtvDesc.Format = mFormatInfo.rtvFormat;
+ rtvDesc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE2DARRAY;
+ rtvDesc.Texture2DArray.MipSlice = mTopLevel + level;
rtvDesc.Texture2DArray.FirstArraySlice = faceIndex;
- rtvDesc.Texture2DArray.ArraySize = 1;
+ rtvDesc.Texture2DArray.ArraySize = 1;
- ID3D11RenderTargetView *rtv;
- result = device->CreateRenderTargetView(texture, &rtvDesc, &rtv);
+ d3d11::RenderTargetView rtv;
+ ANGLE_TRY(mRenderer->allocateResource(rtvDesc, texture->get(), &rtv));
+ rtv.setDebugName("TexStorageCube.RenderTargetRTV");
- ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
- if (FAILED(result))
- {
- SafeRelease(srv);
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal render target view for texture storage, result: 0x%X.", result);
- }
-
- d3d11::SetDebugName(rtv, "TexStorageCube.RenderTargetRTV");
-
- mRenderTarget[faceIndex][level] = new TextureRenderTarget11(rtv, texture, srv, mInternalFormat, getLevelWidth(level), getLevelHeight(level), 1, 0);
-
- // RenderTarget will take ownership of these resources
- SafeRelease(rtv);
- SafeRelease(srv);
+ mRenderTarget[faceIndex][level].reset(new TextureRenderTarget11(
+ std::move(rtv), *texture, srv, blitSRV, mFormatInfo.internalFormat, getFormatSet(),
+ getLevelWidth(level), getLevelHeight(level), 1, 0));
}
- else if (mDepthStencilFormat != DXGI_FORMAT_UNKNOWN)
+ else if (mFormatInfo.dsvFormat != DXGI_FORMAT_UNKNOWN)
{
D3D11_DEPTH_STENCIL_VIEW_DESC dsvDesc;
- dsvDesc.Format = mDepthStencilFormat;
- dsvDesc.ViewDimension = D3D11_DSV_DIMENSION_TEXTURE2DARRAY;
- dsvDesc.Flags = 0;
- dsvDesc.Texture2DArray.MipSlice = mTopLevel + level;
+ dsvDesc.Format = mFormatInfo.dsvFormat;
+ dsvDesc.ViewDimension = D3D11_DSV_DIMENSION_TEXTURE2DARRAY;
+ dsvDesc.Flags = 0;
+ dsvDesc.Texture2DArray.MipSlice = mTopLevel + level;
dsvDesc.Texture2DArray.FirstArraySlice = faceIndex;
- dsvDesc.Texture2DArray.ArraySize = 1;
-
- ID3D11DepthStencilView *dsv;
- result = device->CreateDepthStencilView(texture, &dsvDesc, &dsv);
-
- ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
- if (FAILED(result))
- {
- SafeRelease(srv);
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal depth stencil view for texture storage, result: 0x%X.", result);
- }
+ dsvDesc.Texture2DArray.ArraySize = 1;
- d3d11::SetDebugName(dsv, "TexStorageCube.RenderTargetDSV");
+ d3d11::DepthStencilView dsv;
+ ANGLE_TRY(mRenderer->allocateResource(dsvDesc, texture->get(), &dsv));
+ dsv.setDebugName("TexStorageCube.RenderTargetDSV");
- mRenderTarget[faceIndex][level] = new TextureRenderTarget11(dsv, texture, srv, mInternalFormat, getLevelWidth(level), getLevelHeight(level), 1, 0);
-
- // RenderTarget will take ownership of these resources
- SafeRelease(dsv);
- SafeRelease(srv);
+ mRenderTarget[faceIndex][level].reset(new TextureRenderTarget11(
+ std::move(dsv), *texture, srv, mFormatInfo.internalFormat, getFormatSet(),
+ getLevelWidth(level), getLevelHeight(level), 1, 0));
}
else
{
@@ -2239,215 +2120,237 @@ gl::Error TextureStorage11_Cube::getRenderTarget(const gl::ImageIndex &index, Re
}
ASSERT(outRT);
- *outRT = mRenderTarget[faceIndex][level];
- return gl::Error(GL_NO_ERROR);
+ *outRT = mRenderTarget[faceIndex][level].get();
+ return gl::NoError();
}
-gl::Error TextureStorage11_Cube::createSRV(int baseLevel, int mipLevels, DXGI_FORMAT format, ID3D11Resource *texture,
- ID3D11ShaderResourceView **outSRV) const
+gl::Error TextureStorage11_Cube::createSRV(const gl::Context *context,
+ int baseLevel,
+ int mipLevels,
+ DXGI_FORMAT format,
+ const TextureHelper11 &texture,
+ d3d11::SharedSRV *outSRV)
{
ASSERT(outSRV);
D3D11_SHADER_RESOURCE_VIEW_DESC srvDesc;
srvDesc.Format = format;
- // Unnormalized integer cube maps are not supported by DX11; we emulate them as an array of six 2D textures
- const d3d11::DXGIFormat &dxgiFormatInfo = d3d11::GetDXGIFormatInfo(format);
- if (dxgiFormatInfo.componentType == GL_INT || dxgiFormatInfo.componentType == GL_UNSIGNED_INT)
+ // Unnormalized integer cube maps are not supported by DX11; we emulate them as an array of six
+ // 2D textures
+ const GLenum componentType = d3d11::GetComponentType(format);
+ if (componentType == GL_INT || componentType == GL_UNSIGNED_INT)
{
- srvDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2DARRAY;
+ srvDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2DARRAY;
srvDesc.Texture2DArray.MostDetailedMip = mTopLevel + baseLevel;
srvDesc.Texture2DArray.MipLevels = mipLevels;
srvDesc.Texture2DArray.FirstArraySlice = 0;
- srvDesc.Texture2DArray.ArraySize = CUBE_FACE_COUNT;
+ srvDesc.Texture2DArray.ArraySize = gl::CUBE_FACE_COUNT;
}
else
{
- srvDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURECUBE;
- srvDesc.TextureCube.MipLevels = mipLevels;
+ srvDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURECUBE;
+ srvDesc.TextureCube.MipLevels = mipLevels;
srvDesc.TextureCube.MostDetailedMip = mTopLevel + baseLevel;
}
- ID3D11Resource *srvTexture = texture;
+ const TextureHelper11 *srvTexture = &texture;
if (mRenderer->getWorkarounds().zeroMaxLodWorkaround)
{
ASSERT(mTopLevel == 0);
ASSERT(baseLevel == 0);
- // This code also assumes that the incoming texture equals either mLevelZeroTexture or mTexture.
+ // This code also assumes that the incoming texture equals either mLevelZeroTexture or
+ // mTexture.
if (mipLevels == 1 && mMipLevels > 1)
{
// We must use a SRV on the level-zero-only texture.
- ASSERT(mLevelZeroTexture != NULL && texture == mLevelZeroTexture);
- srvTexture = mLevelZeroTexture;
+ ANGLE_TRY(ensureTextureExists(1));
+ srvTexture = &mLevelZeroTexture;
}
else
{
ASSERT(mipLevels == static_cast<int>(mMipLevels));
- ASSERT(mTexture != NULL && texture == mTexture);
- srvTexture = mTexture;
+ ASSERT(mTexture.valid() && texture == mTexture);
+ srvTexture = &mTexture;
}
}
- ID3D11Device *device = mRenderer->getDevice();
- HRESULT result = device->CreateShaderResourceView(srvTexture, &srvDesc, outSRV);
-
- ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal texture storage SRV, result: 0x%X.", result);
- }
-
- d3d11::SetDebugName(*outSRV, "TexStorageCube.SRV");
+ ANGLE_TRY(mRenderer->allocateResource(srvDesc, srvTexture->get(), outSRV));
+ outSRV->setDebugName("TexStorageCube.SRV");
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error TextureStorage11_Cube::getSwizzleTexture(ID3D11Resource **outTexture)
+gl::Error TextureStorage11_Cube::getSwizzleTexture(const TextureHelper11 **outTexture)
{
ASSERT(outTexture);
- if (!mSwizzleTexture)
+ if (!mSwizzleTexture.valid())
{
- ID3D11Device *device = mRenderer->getDevice();
+ const auto &format = mFormatInfo.getSwizzleFormat(mRenderer->getRenderer11DeviceCaps());
D3D11_TEXTURE2D_DESC desc;
- desc.Width = mTextureWidth;
- desc.Height = mTextureHeight;
- desc.MipLevels = mMipLevels;
- desc.ArraySize = CUBE_FACE_COUNT;
- desc.Format = mSwizzleTextureFormat;
- desc.SampleDesc.Count = 1;
+ desc.Width = mTextureWidth;
+ desc.Height = mTextureHeight;
+ desc.MipLevels = mMipLevels;
+ desc.ArraySize = gl::CUBE_FACE_COUNT;
+ desc.Format = format.texFormat;
+ desc.SampleDesc.Count = 1;
desc.SampleDesc.Quality = 0;
- desc.Usage = D3D11_USAGE_DEFAULT;
- desc.BindFlags = D3D11_BIND_SHADER_RESOURCE | D3D11_BIND_RENDER_TARGET;
- desc.CPUAccessFlags = 0;
- desc.MiscFlags = D3D11_RESOURCE_MISC_TEXTURECUBE;
-
- HRESULT result = device->CreateTexture2D(&desc, NULL, &mSwizzleTexture);
-
- ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal swizzle texture, result: 0x%X.", result);
- }
+ desc.Usage = D3D11_USAGE_DEFAULT;
+ desc.BindFlags = D3D11_BIND_SHADER_RESOURCE | D3D11_BIND_RENDER_TARGET;
+ desc.CPUAccessFlags = 0;
+ desc.MiscFlags = D3D11_RESOURCE_MISC_TEXTURECUBE;
- d3d11::SetDebugName(*outTexture, "TexStorageCube.SwizzleTexture");
+ ANGLE_TRY(mRenderer->allocateTexture(desc, format, &mSwizzleTexture));
+ mSwizzleTexture.setDebugName("TexStorageCube.SwizzleTexture");
}
- *outTexture = mSwizzleTexture;
- return gl::Error(GL_NO_ERROR);
+ *outTexture = &mSwizzleTexture;
+ return gl::NoError();
}
-gl::Error TextureStorage11_Cube::getSwizzleRenderTarget(int mipLevel, ID3D11RenderTargetView **outRTV)
+gl::Error TextureStorage11_Cube::getSwizzleRenderTarget(int mipLevel,
+ const d3d11::RenderTargetView **outRTV)
{
ASSERT(mipLevel >= 0 && mipLevel < getLevelCount());
ASSERT(outRTV);
- if (!mSwizzleRenderTargets[mipLevel])
+ if (!mSwizzleRenderTargets[mipLevel].valid())
{
- ID3D11Resource *swizzleTexture = NULL;
- gl::Error error = getSwizzleTexture(&swizzleTexture);
- if (error.isError())
- {
- return error;
- }
-
- ID3D11Device *device = mRenderer->getDevice();
+ const TextureHelper11 *swizzleTexture = nullptr;
+ ANGLE_TRY(getSwizzleTexture(&swizzleTexture));
D3D11_RENDER_TARGET_VIEW_DESC rtvDesc;
- rtvDesc.Format = mSwizzleRenderTargetFormat;
- rtvDesc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE2DARRAY;
- rtvDesc.Texture2DArray.MipSlice = mTopLevel + mipLevel;
+ rtvDesc.Format =
+ mFormatInfo.getSwizzleFormat(mRenderer->getRenderer11DeviceCaps()).rtvFormat;
+ rtvDesc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE2DARRAY;
+ rtvDesc.Texture2DArray.MipSlice = mTopLevel + mipLevel;
rtvDesc.Texture2DArray.FirstArraySlice = 0;
- rtvDesc.Texture2DArray.ArraySize = CUBE_FACE_COUNT;
-
- HRESULT result = device->CreateRenderTargetView(mSwizzleTexture, &rtvDesc, &mSwizzleRenderTargets[mipLevel]);
+ rtvDesc.Texture2DArray.ArraySize = gl::CUBE_FACE_COUNT;
- ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal swizzle render target view, result: 0x%X.", result);
- }
+ ANGLE_TRY(mRenderer->allocateResource(rtvDesc, mSwizzleTexture.get(),
+ &mSwizzleRenderTargets[mipLevel]));
}
- *outRTV = mSwizzleRenderTargets[mipLevel];
- return gl::Error(GL_NO_ERROR);
+ *outRTV = &mSwizzleRenderTargets[mipLevel];
+ return gl::NoError();
}
-TextureStorage11_3D::TextureStorage11_3D(Renderer11 *renderer, GLenum internalformat, bool renderTarget,
- GLsizei width, GLsizei height, GLsizei depth, int levels)
- : TextureStorage11(renderer,
- GetTextureBindFlags(internalformat, renderer->getRenderer11DeviceCaps(), renderTarget),
- GetTextureMiscFlags(internalformat, renderer->getRenderer11DeviceCaps(), renderTarget, levels))
+gl::Error TextureStorage11::initDropStencilTexture(const gl::Context *context,
+ const gl::ImageIndexIterator &it)
{
- mTexture = NULL;
- mSwizzleTexture = NULL;
+ const TextureHelper11 *sourceTexture = nullptr;
+ ANGLE_TRY(getResource(context, &sourceTexture));
- for (unsigned int i = 0; i < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS; i++)
+ gl::ImageIndexIterator itCopy = it;
+
+ while (itCopy.hasNext())
{
- mAssociatedImages[i] = NULL;
- mLevelRenderTargets[i] = NULL;
- mSwizzleRenderTargets[i] = NULL;
+ gl::ImageIndex index = itCopy.next();
+ gl::Box wholeArea(0, 0, 0, getLevelWidth(index.mipIndex), getLevelHeight(index.mipIndex),
+ 1);
+ gl::Extents wholeSize(wholeArea.width, wholeArea.height, 1);
+ UINT subresource = getSubresourceIndex(index);
+ ANGLE_TRY(mRenderer->getBlitter()->copyDepthStencil(
+ *sourceTexture, subresource, wholeArea, wholeSize, mDropStencilTexture, subresource,
+ wholeArea, wholeSize, nullptr));
}
- mInternalFormat = internalformat;
+ return gl::NoError();
+}
- const d3d11::TextureFormat &formatInfo = d3d11::GetTextureFormatInfo(internalformat, renderer->getRenderer11DeviceCaps());
- mTextureFormat = formatInfo.texFormat;
- mShaderResourceFormat = formatInfo.srvFormat;
- mDepthStencilFormat = formatInfo.dsvFormat;
- mRenderTargetFormat = formatInfo.rtvFormat;
- mSwizzleTextureFormat = formatInfo.swizzleTexFormat;
- mSwizzleShaderResourceFormat = formatInfo.swizzleSRVFormat;
- mSwizzleRenderTargetFormat = formatInfo.swizzleRTVFormat;
+gl::ErrorOrResult<TextureStorage11::DropStencil> TextureStorage11_Cube::ensureDropStencilTexture(
+ const gl::Context *context)
+{
+ if (mDropStencilTexture.valid())
+ {
+ return DropStencil::ALREADY_EXISTS;
+ }
+
+ D3D11_TEXTURE2D_DESC dropDesc = {};
+ dropDesc.ArraySize = 6;
+ dropDesc.BindFlags = D3D11_BIND_SHADER_RESOURCE | D3D11_BIND_DEPTH_STENCIL;
+ dropDesc.CPUAccessFlags = 0;
+ dropDesc.Format = DXGI_FORMAT_R32_TYPELESS;
+ dropDesc.Height = mTextureHeight;
+ dropDesc.MipLevels = mMipLevels;
+ dropDesc.MiscFlags = D3D11_RESOURCE_MISC_TEXTURECUBE;
+ dropDesc.SampleDesc.Count = 1;
+ dropDesc.SampleDesc.Quality = 0;
+ dropDesc.Usage = D3D11_USAGE_DEFAULT;
+ dropDesc.Width = mTextureWidth;
+
+ const auto &format =
+ d3d11::Format::Get(GL_DEPTH_COMPONENT32F, mRenderer->getRenderer11DeviceCaps());
+ ANGLE_TRY(mRenderer->allocateTexture(dropDesc, format, &mDropStencilTexture));
+ mDropStencilTexture.setDebugName("TexStorageCube.DropStencil");
+
+ ANGLE_TRY(initDropStencilTexture(context, gl::ImageIndexIterator::MakeCube(0, mMipLevels)));
+
+ return DropStencil::CREATED;
+}
+
+TextureStorage11_3D::TextureStorage11_3D(Renderer11 *renderer,
+ GLenum internalformat,
+ bool renderTarget,
+ GLsizei width,
+ GLsizei height,
+ GLsizei depth,
+ int levels)
+ : TextureStorage11(
+ renderer,
+ GetTextureBindFlags(internalformat, renderer->getRenderer11DeviceCaps(), renderTarget),
+ GetTextureMiscFlags(internalformat,
+ renderer->getRenderer11DeviceCaps(),
+ renderTarget,
+ levels),
+ internalformat)
+{
+ for (unsigned int i = 0; i < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS; i++)
+ {
+ mAssociatedImages[i] = nullptr;
+ mLevelRenderTargets[i] = nullptr;
+ }
// adjust size if needed for compressed textures
- d3d11::MakeValidSize(false, mTextureFormat, &width, &height, &mTopLevel);
+ d3d11::MakeValidSize(false, mFormatInfo.texFormat, &width, &height, &mTopLevel);
- mMipLevels = mTopLevel + levels;
- mTextureWidth = width;
+ mMipLevels = mTopLevel + levels;
+ mTextureWidth = width;
mTextureHeight = height;
- mTextureDepth = depth;
+ mTextureDepth = depth;
}
-TextureStorage11_3D::~TextureStorage11_3D()
+gl::Error TextureStorage11_3D::onDestroy(const gl::Context *context)
{
for (unsigned i = 0; i < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS; i++)
{
- if (mAssociatedImages[i] != NULL)
+ if (mAssociatedImages[i] != nullptr)
{
- bool imageAssociationCorrect = mAssociatedImages[i]->isAssociatedStorageValid(this);
- ASSERT(imageAssociationCorrect);
+ mAssociatedImages[i]->verifyAssociatedStorageValid(this);
- if (imageAssociationCorrect)
- {
- // We must let the Images recover their data before we delete it from the TextureStorage.
- mAssociatedImages[i]->recoverFromAssociatedStorage();
- }
+ // We must let the Images recover their data before we delete it from the
+ // TextureStorage.
+ ANGLE_TRY(mAssociatedImages[i]->recoverFromAssociatedStorage(context));
}
}
- SafeRelease(mTexture);
- SafeRelease(mSwizzleTexture);
+ InvalidateRenderTargetContainer(context, &mLevelRenderTargets);
+ InvalidateRenderTargetContainer(context, &mLevelLayerRenderTargets);
- for (RenderTargetMap::iterator i = mLevelLayerRenderTargets.begin(); i != mLevelLayerRenderTargets.end(); i++)
- {
- SafeDelete(i->second);
- }
- mLevelLayerRenderTargets.clear();
+ return gl::NoError();
+}
- for (unsigned int i = 0; i < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS; i++)
- {
- SafeDelete(mLevelRenderTargets[i]);
- SafeRelease(mSwizzleRenderTargets[i]);
- }
+TextureStorage11_3D::~TextureStorage11_3D()
+{
}
-void TextureStorage11_3D::associateImage(Image11* image, const gl::ImageIndex &index)
+void TextureStorage11_3D::associateImage(Image11 *image, const gl::ImageIndex &index)
{
- GLint level = index.mipIndex;
+ const GLint level = index.mipIndex;
ASSERT(0 <= level && level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS);
@@ -2457,676 +2360,796 @@ void TextureStorage11_3D::associateImage(Image11* image, const gl::ImageIndex &i
}
}
-bool TextureStorage11_3D::isAssociatedImageValid(const gl::ImageIndex &index, Image11* expectedImage)
+void TextureStorage11_3D::verifyAssociatedImageValid(const gl::ImageIndex &index,
+ Image11 *expectedImage)
{
- GLint level = index.mipIndex;
-
- if (0 <= level && level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS)
- {
- // This validation check should never return false. It means the Image/TextureStorage association is broken.
- bool retValue = (mAssociatedImages[level] == expectedImage);
- ASSERT(retValue);
- return retValue;
- }
+ const GLint level = index.mipIndex;
- return false;
+ ASSERT(0 <= level && level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS);
+ // This validation check should never return false. It means the Image/TextureStorage
+ // association is broken.
+ ASSERT(mAssociatedImages[level] == expectedImage);
}
// disassociateImage allows an Image to end its association with a Storage.
-void TextureStorage11_3D::disassociateImage(const gl::ImageIndex &index, Image11* expectedImage)
+void TextureStorage11_3D::disassociateImage(const gl::ImageIndex &index, Image11 *expectedImage)
{
- GLint level = index.mipIndex;
+ const GLint level = index.mipIndex;
ASSERT(0 <= level && level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS);
-
- if (0 <= level && level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS)
- {
- ASSERT(mAssociatedImages[level] == expectedImage);
-
- if (mAssociatedImages[level] == expectedImage)
- {
- mAssociatedImages[level] = NULL;
- }
- }
+ ASSERT(mAssociatedImages[level] == expectedImage);
+ mAssociatedImages[level] = nullptr;
}
-// releaseAssociatedImage prepares the Storage for a new Image association. It lets the old Image recover its data before ending the association.
-gl::Error TextureStorage11_3D::releaseAssociatedImage(const gl::ImageIndex &index, Image11* incomingImage)
+// releaseAssociatedImage prepares the Storage for a new Image association. It lets the old Image
+// recover its data before ending the association.
+gl::Error TextureStorage11_3D::releaseAssociatedImage(const gl::Context *context,
+ const gl::ImageIndex &index,
+ Image11 *incomingImage)
{
- GLint level = index.mipIndex;
+ const GLint level = index.mipIndex;
ASSERT((0 <= level && level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS));
if (0 <= level && level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS)
{
// No need to let the old Image recover its data, if it is also the incoming Image.
- if (mAssociatedImages[level] != NULL && mAssociatedImages[level] != incomingImage)
+ if (mAssociatedImages[level] != nullptr && mAssociatedImages[level] != incomingImage)
{
- // Ensure that the Image is still associated with this TextureStorage. This should be true.
- bool imageAssociationCorrect = mAssociatedImages[level]->isAssociatedStorageValid(this);
- ASSERT(imageAssociationCorrect);
+ // Ensure that the Image is still associated with this TextureStorage.
+ mAssociatedImages[level]->verifyAssociatedStorageValid(this);
- if (imageAssociationCorrect)
- {
- // Force the image to recover from storage before its data is overwritten.
- // This will reset mAssociatedImages[level] to NULL too.
- gl::Error error = mAssociatedImages[level]->recoverFromAssociatedStorage();
- if (error.isError())
- {
- return error;
- }
- }
+ // Force the image to recover from storage before its data is overwritten.
+ // This will reset mAssociatedImages[level] to nullptr too.
+ ANGLE_TRY(mAssociatedImages[level]->recoverFromAssociatedStorage(context));
}
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error TextureStorage11_3D::getResource(ID3D11Resource **outResource)
+gl::Error TextureStorage11_3D::getResource(const gl::Context *context,
+ const TextureHelper11 **outResource)
{
- // If the width, height or depth are not positive this should be treated as an incomplete texture
- // we handle that here by skipping the d3d texture creation
- if (mTexture == NULL && mTextureWidth > 0 && mTextureHeight > 0 && mTextureDepth > 0)
+ // If the width, height or depth are not positive this should be treated as an incomplete
+ // texture. We handle that here by skipping the d3d texture creation.
+ if (!mTexture.valid() && mTextureWidth > 0 && mTextureHeight > 0 && mTextureDepth > 0)
{
ASSERT(mMipLevels > 0);
- ID3D11Device *device = mRenderer->getDevice();
-
D3D11_TEXTURE3D_DESC desc;
- desc.Width = mTextureWidth;
- desc.Height = mTextureHeight;
- desc.Depth = mTextureDepth;
- desc.MipLevels = mMipLevels;
- desc.Format = mTextureFormat;
- desc.Usage = D3D11_USAGE_DEFAULT;
- desc.BindFlags = getBindFlags();
+ desc.Width = mTextureWidth;
+ desc.Height = mTextureHeight;
+ desc.Depth = mTextureDepth;
+ desc.MipLevels = mMipLevels;
+ desc.Format = mFormatInfo.texFormat;
+ desc.Usage = D3D11_USAGE_DEFAULT;
+ desc.BindFlags = getBindFlags();
desc.CPUAccessFlags = 0;
- desc.MiscFlags = getMiscFlags();
+ desc.MiscFlags = getMiscFlags();
- HRESULT result = device->CreateTexture3D(&desc, NULL, &mTexture);
-
- // this can happen from windows TDR
- if (d3d11::isDeviceLostError(result))
- {
- mRenderer->notifyDeviceLost();
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create 3D texture storage, result: 0x%X.", result);
- }
- else if (FAILED(result))
- {
- ASSERT(result == E_OUTOFMEMORY);
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create 3D texture storage, result: 0x%X.", result);
- }
-
- d3d11::SetDebugName(mTexture, "TexStorage3D.Texture");
+ ANGLE_TRY(mRenderer->allocateTexture(desc, mFormatInfo, &mTexture));
+ mTexture.setDebugName("TexStorage3D.Texture");
}
- *outResource = mTexture;
- return gl::Error(GL_NO_ERROR);
+ *outResource = &mTexture;
+ return gl::NoError();
}
-gl::Error TextureStorage11_3D::createSRV(int baseLevel, int mipLevels, DXGI_FORMAT format, ID3D11Resource *texture,
- ID3D11ShaderResourceView **outSRV) const
+gl::Error TextureStorage11_3D::createSRV(const gl::Context *context,
+ int baseLevel,
+ int mipLevels,
+ DXGI_FORMAT format,
+ const TextureHelper11 &texture,
+ d3d11::SharedSRV *outSRV)
{
ASSERT(outSRV);
D3D11_SHADER_RESOURCE_VIEW_DESC srvDesc;
- srvDesc.Format = format;
- srvDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE3D;
+ srvDesc.Format = format;
+ srvDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE3D;
srvDesc.Texture3D.MostDetailedMip = baseLevel;
- srvDesc.Texture3D.MipLevels = mipLevels;
-
- ID3D11Device *device = mRenderer->getDevice();
- HRESULT result = device->CreateShaderResourceView(texture, &srvDesc, outSRV);
-
- ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal texture storage SRV, result: 0x%X.", result);
- }
+ srvDesc.Texture3D.MipLevels = mipLevels;
- d3d11::SetDebugName(*outSRV, "TexStorage3D.SRV");
+ ANGLE_TRY(mRenderer->allocateResource(srvDesc, texture.get(), outSRV));
+ outSRV->setDebugName("TexStorage3D.SRV");
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error TextureStorage11_3D::getRenderTarget(const gl::ImageIndex &index, RenderTargetD3D **outRT)
+gl::Error TextureStorage11_3D::getRenderTarget(const gl::Context *context,
+ const gl::ImageIndex &index,
+ RenderTargetD3D **outRT)
{
- int mipLevel = index.mipIndex;
+ const int mipLevel = index.mipIndex;
ASSERT(mipLevel >= 0 && mipLevel < getLevelCount());
- ASSERT(mRenderTargetFormat != DXGI_FORMAT_UNKNOWN);
+ ASSERT(mFormatInfo.rtvFormat != DXGI_FORMAT_UNKNOWN);
if (!index.hasLayer())
{
if (!mLevelRenderTargets[mipLevel])
{
- ID3D11Resource *texture = NULL;
- gl::Error error = getResource(&texture);
- if (error.isError())
- {
- return error;
- }
+ const TextureHelper11 *texture = nullptr;
+ ANGLE_TRY(getResource(context, &texture));
- ID3D11ShaderResourceView *srv = NULL;
- error = getSRVLevel(mipLevel, &srv);
- if (error.isError())
- {
- return error;
- }
+ const d3d11::SharedSRV *srv = nullptr;
+ ANGLE_TRY(getSRVLevel(context, mipLevel, false, &srv));
- ID3D11Device *device = mRenderer->getDevice();
+ const d3d11::SharedSRV *blitSRV = nullptr;
+ ANGLE_TRY(getSRVLevel(context, mipLevel, true, &blitSRV));
D3D11_RENDER_TARGET_VIEW_DESC rtvDesc;
- rtvDesc.Format = mRenderTargetFormat;
- rtvDesc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE3D;
- rtvDesc.Texture3D.MipSlice = mTopLevel + mipLevel;
+ rtvDesc.Format = mFormatInfo.rtvFormat;
+ rtvDesc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE3D;
+ rtvDesc.Texture3D.MipSlice = mTopLevel + mipLevel;
rtvDesc.Texture3D.FirstWSlice = 0;
- rtvDesc.Texture3D.WSize = static_cast<UINT>(-1);
-
- ID3D11RenderTargetView *rtv;
- HRESULT result = device->CreateRenderTargetView(texture, &rtvDesc, &rtv);
-
- ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
- if (FAILED(result))
- {
- SafeRelease(srv);
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal render target view for texture storage, result: 0x%X.", result);
- }
-
- d3d11::SetDebugName(rtv, "TexStorage3D.RTV");
+ rtvDesc.Texture3D.WSize = static_cast<UINT>(-1);
- mLevelRenderTargets[mipLevel] = new TextureRenderTarget11(rtv, texture, srv, mInternalFormat, getLevelWidth(mipLevel), getLevelHeight(mipLevel), getLevelDepth(mipLevel), 0);
+ d3d11::RenderTargetView rtv;
+ ANGLE_TRY(mRenderer->allocateResource(rtvDesc, texture->get(), &rtv));
+ rtv.setDebugName("TexStorage3D.RTV");
- // RenderTarget will take ownership of these resources
- SafeRelease(rtv);
+ mLevelRenderTargets[mipLevel].reset(new TextureRenderTarget11(
+ std::move(rtv), *texture, *srv, *blitSRV, mFormatInfo.internalFormat,
+ getFormatSet(), getLevelWidth(mipLevel), getLevelHeight(mipLevel),
+ getLevelDepth(mipLevel), 0));
}
ASSERT(outRT);
- *outRT = mLevelRenderTargets[mipLevel];
- return gl::Error(GL_NO_ERROR);
+ *outRT = mLevelRenderTargets[mipLevel].get();
+ return gl::NoError();
}
- else
- {
- int layer = index.layerIndex;
- LevelLayerKey key(mipLevel, layer);
- if (mLevelLayerRenderTargets.find(key) == mLevelLayerRenderTargets.end())
- {
- ID3D11Device *device = mRenderer->getDevice();
- HRESULT result;
+ const int layer = index.layerIndex;
- ID3D11Resource *texture = NULL;
- gl::Error error = getResource(&texture);
- if (error.isError())
- {
- return error;
- }
-
- // TODO, what kind of SRV is expected here?
- ID3D11ShaderResourceView *srv = NULL;
-
- D3D11_RENDER_TARGET_VIEW_DESC rtvDesc;
- rtvDesc.Format = mRenderTargetFormat;
- rtvDesc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE3D;
- rtvDesc.Texture3D.MipSlice = mTopLevel + mipLevel;
- rtvDesc.Texture3D.FirstWSlice = layer;
- rtvDesc.Texture3D.WSize = 1;
-
- ID3D11RenderTargetView *rtv;
- result = device->CreateRenderTargetView(texture, &rtvDesc, &rtv);
-
- ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
- if (FAILED(result))
- {
- SafeRelease(srv); return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal render target view for texture storage, result: 0x%X.", result);
- }
- ASSERT(SUCCEEDED(result));
+ LevelLayerKey key(mipLevel, layer);
+ if (mLevelLayerRenderTargets.find(key) == mLevelLayerRenderTargets.end())
+ {
+ const TextureHelper11 *texture = nullptr;
+ ANGLE_TRY(getResource(context, &texture));
- d3d11::SetDebugName(rtv, "TexStorage3D.LayerRTV");
+ // TODO, what kind of SRV is expected here?
+ const d3d11::SharedSRV srv;
+ const d3d11::SharedSRV blitSRV;
- mLevelLayerRenderTargets[key] = new TextureRenderTarget11(rtv, texture, srv, mInternalFormat, getLevelWidth(mipLevel), getLevelHeight(mipLevel), 1, 0);
+ D3D11_RENDER_TARGET_VIEW_DESC rtvDesc;
+ rtvDesc.Format = mFormatInfo.rtvFormat;
+ rtvDesc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE3D;
+ rtvDesc.Texture3D.MipSlice = mTopLevel + mipLevel;
+ rtvDesc.Texture3D.FirstWSlice = layer;
+ rtvDesc.Texture3D.WSize = 1;
- // RenderTarget will take ownership of these resources
- SafeRelease(rtv);
- }
+ d3d11::RenderTargetView rtv;
+ ANGLE_TRY(mRenderer->allocateResource(rtvDesc, texture->get(), &rtv));
+ rtv.setDebugName("TexStorage3D.LayerRTV");
- ASSERT(outRT);
- *outRT = mLevelLayerRenderTargets[key];
- return gl::Error(GL_NO_ERROR);
+ mLevelLayerRenderTargets[key].reset(new TextureRenderTarget11(
+ std::move(rtv), *texture, srv, blitSRV, mFormatInfo.internalFormat, getFormatSet(),
+ getLevelWidth(mipLevel), getLevelHeight(mipLevel), 1, 0));
}
+
+ ASSERT(outRT);
+ *outRT = mLevelLayerRenderTargets[key].get();
+ return gl::NoError();
}
-gl::Error TextureStorage11_3D::getSwizzleTexture(ID3D11Resource **outTexture)
+gl::Error TextureStorage11_3D::getSwizzleTexture(const TextureHelper11 **outTexture)
{
ASSERT(outTexture);
- if (!mSwizzleTexture)
+ if (!mSwizzleTexture.valid())
{
- ID3D11Device *device = mRenderer->getDevice();
+ const auto &format = mFormatInfo.getSwizzleFormat(mRenderer->getRenderer11DeviceCaps());
D3D11_TEXTURE3D_DESC desc;
- desc.Width = mTextureWidth;
- desc.Height = mTextureHeight;
- desc.Depth = mTextureDepth;
- desc.MipLevels = mMipLevels;
- desc.Format = mSwizzleTextureFormat;
- desc.Usage = D3D11_USAGE_DEFAULT;
- desc.BindFlags = D3D11_BIND_SHADER_RESOURCE | D3D11_BIND_RENDER_TARGET;
+ desc.Width = mTextureWidth;
+ desc.Height = mTextureHeight;
+ desc.Depth = mTextureDepth;
+ desc.MipLevels = mMipLevels;
+ desc.Format = format.texFormat;
+ desc.Usage = D3D11_USAGE_DEFAULT;
+ desc.BindFlags = D3D11_BIND_SHADER_RESOURCE | D3D11_BIND_RENDER_TARGET;
desc.CPUAccessFlags = 0;
- desc.MiscFlags = 0;
-
- HRESULT result = device->CreateTexture3D(&desc, NULL, &mSwizzleTexture);
-
- ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal swizzle texture, result: 0x%X.", result);
- }
+ desc.MiscFlags = 0;
- d3d11::SetDebugName(mSwizzleTexture, "TexStorage3D.SwizzleTexture");
+ ANGLE_TRY(mRenderer->allocateTexture(desc, format, &mSwizzleTexture));
+ mSwizzleTexture.setDebugName("TexStorage3D.SwizzleTexture");
}
- *outTexture = mSwizzleTexture;
- return gl::Error(GL_NO_ERROR);
+ *outTexture = &mSwizzleTexture;
+ return gl::NoError();
}
-gl::Error TextureStorage11_3D::getSwizzleRenderTarget(int mipLevel, ID3D11RenderTargetView **outRTV)
+gl::Error TextureStorage11_3D::getSwizzleRenderTarget(int mipLevel,
+ const d3d11::RenderTargetView **outRTV)
{
ASSERT(mipLevel >= 0 && mipLevel < getLevelCount());
ASSERT(outRTV);
- if (!mSwizzleRenderTargets[mipLevel])
+ if (!mSwizzleRenderTargets[mipLevel].valid())
{
- ID3D11Resource *swizzleTexture = NULL;
- gl::Error error = getSwizzleTexture(&swizzleTexture);
- if (error.isError())
- {
- return error;
- }
-
- ID3D11Device *device = mRenderer->getDevice();
+ const TextureHelper11 *swizzleTexture = nullptr;
+ ANGLE_TRY(getSwizzleTexture(&swizzleTexture));
D3D11_RENDER_TARGET_VIEW_DESC rtvDesc;
- rtvDesc.Format = mSwizzleRenderTargetFormat;
- rtvDesc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE3D;
- rtvDesc.Texture3D.MipSlice = mTopLevel + mipLevel;
+ rtvDesc.Format =
+ mFormatInfo.getSwizzleFormat(mRenderer->getRenderer11DeviceCaps()).rtvFormat;
+ rtvDesc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE3D;
+ rtvDesc.Texture3D.MipSlice = mTopLevel + mipLevel;
rtvDesc.Texture3D.FirstWSlice = 0;
- rtvDesc.Texture3D.WSize = static_cast<UINT>(-1);
+ rtvDesc.Texture3D.WSize = static_cast<UINT>(-1);
- HRESULT result = device->CreateRenderTargetView(mSwizzleTexture, &rtvDesc, &mSwizzleRenderTargets[mipLevel]);
-
- ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal swizzle render target view, result: 0x%X.", result);
- }
-
- d3d11::SetDebugName(mSwizzleTexture, "TexStorage3D.SwizzleRTV");
+ ANGLE_TRY(mRenderer->allocateResource(rtvDesc, mSwizzleTexture.get(),
+ &mSwizzleRenderTargets[mipLevel]));
+ mSwizzleRenderTargets[mipLevel].setDebugName("TexStorage3D.SwizzleRTV");
}
- *outRTV = mSwizzleRenderTargets[mipLevel];
- return gl::Error(GL_NO_ERROR);
+ *outRTV = &mSwizzleRenderTargets[mipLevel];
+ return gl::NoError();
}
-TextureStorage11_2DArray::TextureStorage11_2DArray(Renderer11 *renderer, GLenum internalformat, bool renderTarget,
- GLsizei width, GLsizei height, GLsizei depth, int levels)
- : TextureStorage11(renderer,
- GetTextureBindFlags(internalformat, renderer->getRenderer11DeviceCaps(), renderTarget),
- GetTextureMiscFlags(internalformat, renderer->getRenderer11DeviceCaps(), renderTarget, levels))
+TextureStorage11_2DArray::TextureStorage11_2DArray(Renderer11 *renderer,
+ GLenum internalformat,
+ bool renderTarget,
+ GLsizei width,
+ GLsizei height,
+ GLsizei depth,
+ int levels)
+ : TextureStorage11(
+ renderer,
+ GetTextureBindFlags(internalformat, renderer->getRenderer11DeviceCaps(), renderTarget),
+ GetTextureMiscFlags(internalformat,
+ renderer->getRenderer11DeviceCaps(),
+ renderTarget,
+ levels),
+ internalformat)
{
- mTexture = NULL;
- mSwizzleTexture = NULL;
-
- for (unsigned int level = 0; level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS; level++)
- {
- mSwizzleRenderTargets[level] = NULL;
- }
-
- mInternalFormat = internalformat;
-
- const d3d11::TextureFormat &formatInfo = d3d11::GetTextureFormatInfo(internalformat, renderer->getRenderer11DeviceCaps());
- mTextureFormat = formatInfo.texFormat;
- mShaderResourceFormat = formatInfo.srvFormat;
- mDepthStencilFormat = formatInfo.dsvFormat;
- mRenderTargetFormat = formatInfo.rtvFormat;
- mSwizzleTextureFormat = formatInfo.swizzleTexFormat;
- mSwizzleShaderResourceFormat = formatInfo.swizzleSRVFormat;
- mSwizzleRenderTargetFormat = formatInfo.swizzleRTVFormat;
-
// adjust size if needed for compressed textures
- d3d11::MakeValidSize(false, mTextureFormat, &width, &height, &mTopLevel);
+ d3d11::MakeValidSize(false, mFormatInfo.texFormat, &width, &height, &mTopLevel);
- mMipLevels = mTopLevel + levels;
- mTextureWidth = width;
+ mMipLevels = mTopLevel + levels;
+ mTextureWidth = width;
mTextureHeight = height;
- mTextureDepth = depth;
+ mTextureDepth = depth;
}
-TextureStorage11_2DArray::~TextureStorage11_2DArray()
+gl::Error TextureStorage11_2DArray::onDestroy(const gl::Context *context)
{
- for (ImageMap::iterator i = mAssociatedImages.begin(); i != mAssociatedImages.end(); i++)
+ for (auto iter : mAssociatedImages)
{
- if (i->second)
+ if (iter.second)
{
- bool imageAssociationCorrect = i->second->isAssociatedStorageValid(this);
- ASSERT(imageAssociationCorrect);
+ iter.second->verifyAssociatedStorageValid(this);
- if (imageAssociationCorrect)
- {
- // We must let the Images recover their data before we delete it from the TextureStorage.
- i->second->recoverFromAssociatedStorage();
- }
+ // We must let the Images recover their data before we delete it from the
+ // TextureStorage.
+ ANGLE_TRY(iter.second->recoverFromAssociatedStorage(context));
}
}
mAssociatedImages.clear();
- SafeRelease(mTexture);
- SafeRelease(mSwizzleTexture);
+ InvalidateRenderTargetContainer(context, &mRenderTargets);
- for (unsigned int level = 0; level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS; level++)
- {
- SafeRelease(mSwizzleRenderTargets[level]);
- }
+ return gl::NoError();
+}
- for (RenderTargetMap::iterator i = mRenderTargets.begin(); i != mRenderTargets.end(); i++)
- {
- SafeDelete(i->second);
- }
- mRenderTargets.clear();
+TextureStorage11_2DArray::~TextureStorage11_2DArray()
+{
}
-void TextureStorage11_2DArray::associateImage(Image11* image, const gl::ImageIndex &index)
+void TextureStorage11_2DArray::associateImage(Image11 *image, const gl::ImageIndex &index)
{
- GLint level = index.mipIndex;
- GLint layerTarget = index.layerIndex;
+ const GLint level = index.mipIndex;
+ const GLint layerTarget = index.layerIndex;
+ const GLint numLayers = index.numLayers;
ASSERT(0 <= level && level < getLevelCount());
if (0 <= level && level < getLevelCount())
{
- LevelLayerKey key(level, layerTarget);
+ LevelLayerRangeKey key(level, layerTarget, numLayers);
mAssociatedImages[key] = image;
}
}
-bool TextureStorage11_2DArray::isAssociatedImageValid(const gl::ImageIndex &index, Image11* expectedImage)
+void TextureStorage11_2DArray::verifyAssociatedImageValid(const gl::ImageIndex &index,
+ Image11 *expectedImage)
{
- GLint level = index.mipIndex;
- GLint layerTarget = index.layerIndex;
+ const GLint level = index.mipIndex;
+ const GLint layerTarget = index.layerIndex;
+ const GLint numLayers = index.numLayers;
- LevelLayerKey key(level, layerTarget);
+ LevelLayerRangeKey key(level, layerTarget, numLayers);
- // This validation check should never return false. It means the Image/TextureStorage association is broken.
- bool retValue = (mAssociatedImages.find(key) != mAssociatedImages.end() && (mAssociatedImages[key] == expectedImage));
+ // This validation check should never return false. It means the Image/TextureStorage
+ // association is broken.
+ bool retValue = (mAssociatedImages.find(key) != mAssociatedImages.end() &&
+ (mAssociatedImages[key] == expectedImage));
ASSERT(retValue);
- return retValue;
}
// disassociateImage allows an Image to end its association with a Storage.
-void TextureStorage11_2DArray::disassociateImage(const gl::ImageIndex &index, Image11* expectedImage)
+void TextureStorage11_2DArray::disassociateImage(const gl::ImageIndex &index,
+ Image11 *expectedImage)
{
- GLint level = index.mipIndex;
- GLint layerTarget = index.layerIndex;
+ const GLint level = index.mipIndex;
+ const GLint layerTarget = index.layerIndex;
+ const GLint numLayers = index.numLayers;
- LevelLayerKey key(level, layerTarget);
+ LevelLayerRangeKey key(level, layerTarget, numLayers);
- bool imageAssociationCorrect = (mAssociatedImages.find(key) != mAssociatedImages.end() && (mAssociatedImages[key] == expectedImage));
+ bool imageAssociationCorrect = (mAssociatedImages.find(key) != mAssociatedImages.end() &&
+ (mAssociatedImages[key] == expectedImage));
ASSERT(imageAssociationCorrect);
-
- if (imageAssociationCorrect)
- {
- mAssociatedImages[key] = NULL;
- }
+ mAssociatedImages[key] = nullptr;
}
-// releaseAssociatedImage prepares the Storage for a new Image association. It lets the old Image recover its data before ending the association.
-gl::Error TextureStorage11_2DArray::releaseAssociatedImage(const gl::ImageIndex &index, Image11* incomingImage)
+// releaseAssociatedImage prepares the Storage for a new Image association. It lets the old Image
+// recover its data before ending the association.
+gl::Error TextureStorage11_2DArray::releaseAssociatedImage(const gl::Context *context,
+ const gl::ImageIndex &index,
+ Image11 *incomingImage)
{
- GLint level = index.mipIndex;
- GLint layerTarget = index.layerIndex;
+ const GLint level = index.mipIndex;
+ const GLint layerTarget = index.layerIndex;
+ const GLint numLayers = index.numLayers;
- LevelLayerKey key(level, layerTarget);
+ LevelLayerRangeKey key(level, layerTarget, numLayers);
if (mAssociatedImages.find(key) != mAssociatedImages.end())
{
- if (mAssociatedImages[key] != NULL && mAssociatedImages[key] != incomingImage)
+ if (mAssociatedImages[key] != nullptr && mAssociatedImages[key] != incomingImage)
{
- // Ensure that the Image is still associated with this TextureStorage. This should be true.
- bool imageAssociationCorrect = mAssociatedImages[key]->isAssociatedStorageValid(this);
- ASSERT(imageAssociationCorrect);
+ // Ensure that the Image is still associated with this TextureStorage.
+ mAssociatedImages[key]->verifyAssociatedStorageValid(this);
- if (imageAssociationCorrect)
- {
- // Force the image to recover from storage before its data is overwritten.
- // This will reset mAssociatedImages[level] to NULL too.
- gl::Error error = mAssociatedImages[key]->recoverFromAssociatedStorage();
- if (error.isError())
- {
- return error;
- }
- }
+ // Force the image to recover from storage before its data is overwritten.
+ // This will reset mAssociatedImages[level] to nullptr too.
+ ANGLE_TRY(mAssociatedImages[key]->recoverFromAssociatedStorage(context));
}
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error TextureStorage11_2DArray::getResource(ID3D11Resource **outResource)
+gl::Error TextureStorage11_2DArray::getResource(const gl::Context *context,
+ const TextureHelper11 **outResource)
{
// if the width, height or depth is not positive this should be treated as an incomplete texture
// we handle that here by skipping the d3d texture creation
- if (mTexture == NULL && mTextureWidth > 0 && mTextureHeight > 0 && mTextureDepth > 0)
+ if (!mTexture.valid() && mTextureWidth > 0 && mTextureHeight > 0 && mTextureDepth > 0)
{
ASSERT(mMipLevels > 0);
- ID3D11Device *device = mRenderer->getDevice();
-
D3D11_TEXTURE2D_DESC desc;
- desc.Width = mTextureWidth;
- desc.Height = mTextureHeight;
- desc.MipLevels = mMipLevels;
- desc.ArraySize = mTextureDepth;
- desc.Format = mTextureFormat;
- desc.SampleDesc.Count = 1;
+ desc.Width = mTextureWidth;
+ desc.Height = mTextureHeight;
+ desc.MipLevels = mMipLevels;
+ desc.ArraySize = mTextureDepth;
+ desc.Format = mFormatInfo.texFormat;
+ desc.SampleDesc.Count = 1;
desc.SampleDesc.Quality = 0;
- desc.Usage = D3D11_USAGE_DEFAULT;
- desc.BindFlags = getBindFlags();
- desc.CPUAccessFlags = 0;
- desc.MiscFlags = getMiscFlags();
-
- HRESULT result = device->CreateTexture2D(&desc, NULL, &mTexture);
-
- // this can happen from windows TDR
- if (d3d11::isDeviceLostError(result))
- {
- mRenderer->notifyDeviceLost();
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create 2D array texture storage, result: 0x%X.", result);
- }
- else if (FAILED(result))
- {
- ASSERT(result == E_OUTOFMEMORY);
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create 2D array texture storage, result: 0x%X.", result);
- }
+ desc.Usage = D3D11_USAGE_DEFAULT;
+ desc.BindFlags = getBindFlags();
+ desc.CPUAccessFlags = 0;
+ desc.MiscFlags = getMiscFlags();
- d3d11::SetDebugName(mTexture, "TexStorage2DArray.Texture");
+ ANGLE_TRY(mRenderer->allocateTexture(desc, mFormatInfo, &mTexture));
+ mTexture.setDebugName("TexStorage2DArray.Texture");
}
- *outResource = mTexture;
- return gl::Error(GL_NO_ERROR);
+ *outResource = &mTexture;
+ return gl::NoError();
}
-gl::Error TextureStorage11_2DArray::createSRV(int baseLevel, int mipLevels, DXGI_FORMAT format, ID3D11Resource *texture,
- ID3D11ShaderResourceView **outSRV) const
+gl::Error TextureStorage11_2DArray::createSRV(const gl::Context *context,
+ int baseLevel,
+ int mipLevels,
+ DXGI_FORMAT format,
+ const TextureHelper11 &texture,
+ d3d11::SharedSRV *outSRV)
{
D3D11_SHADER_RESOURCE_VIEW_DESC srvDesc;
- srvDesc.Format = format;
- srvDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2DARRAY;
+ srvDesc.Format = format;
+ srvDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2DARRAY;
srvDesc.Texture2DArray.MostDetailedMip = mTopLevel + baseLevel;
- srvDesc.Texture2DArray.MipLevels = mipLevels;
+ srvDesc.Texture2DArray.MipLevels = mipLevels;
srvDesc.Texture2DArray.FirstArraySlice = 0;
- srvDesc.Texture2DArray.ArraySize = mTextureDepth;
+ srvDesc.Texture2DArray.ArraySize = mTextureDepth;
- ID3D11Device *device = mRenderer->getDevice();
- HRESULT result = device->CreateShaderResourceView(texture, &srvDesc, outSRV);
+ ANGLE_TRY(mRenderer->allocateResource(srvDesc, texture.get(), outSRV));
+ outSRV->setDebugName("TexStorage2DArray.SRV");
- ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal texture storage SRV, result: 0x%X.", result);
- }
+ return gl::NoError();
+}
+
+gl::Error TextureStorage11_2DArray::createRenderTargetSRV(const TextureHelper11 &texture,
+ const gl::ImageIndex &index,
+ DXGI_FORMAT resourceFormat,
+ d3d11::SharedSRV *srv) const
+{
+ D3D11_SHADER_RESOURCE_VIEW_DESC srvDesc;
+ srvDesc.Format = resourceFormat;
+ srvDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2DARRAY;
+ srvDesc.Texture2DArray.MostDetailedMip = mTopLevel + index.mipIndex;
+ srvDesc.Texture2DArray.MipLevels = 1;
+ srvDesc.Texture2DArray.FirstArraySlice = index.layerIndex;
+ srvDesc.Texture2DArray.ArraySize = index.numLayers;
- d3d11::SetDebugName(*outSRV, "TexStorage2DArray.SRV");
+ ANGLE_TRY(mRenderer->allocateResource(srvDesc, texture.get(), srv));
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-gl::Error TextureStorage11_2DArray::getRenderTarget(const gl::ImageIndex &index, RenderTargetD3D **outRT)
+gl::Error TextureStorage11_2DArray::getRenderTarget(const gl::Context *context,
+ const gl::ImageIndex &index,
+ RenderTargetD3D **outRT)
{
ASSERT(index.hasLayer());
- int mipLevel = index.mipIndex;
- int layer = index.layerIndex;
+ const int mipLevel = index.mipIndex;
+ const int layer = index.layerIndex;
+ const int numLayers = index.numLayers;
ASSERT(mipLevel >= 0 && mipLevel < getLevelCount());
- LevelLayerKey key(mipLevel, layer);
+ LevelLayerRangeKey key(mipLevel, layer, numLayers);
if (mRenderTargets.find(key) == mRenderTargets.end())
{
- ID3D11Device *device = mRenderer->getDevice();
- HRESULT result;
-
- ID3D11Resource *texture = NULL;
- gl::Error error = getResource(&texture);
- if (error.isError())
+ const TextureHelper11 *texture = nullptr;
+ ANGLE_TRY(getResource(context, &texture));
+ d3d11::SharedSRV srv;
+ ANGLE_TRY(createRenderTargetSRV(*texture, index, mFormatInfo.srvFormat, &srv));
+ d3d11::SharedSRV blitSRV;
+ if (mFormatInfo.blitSRVFormat != mFormatInfo.srvFormat)
{
- return error;
+ ANGLE_TRY(createRenderTargetSRV(*texture, index, mFormatInfo.blitSRVFormat, &blitSRV));
}
-
- D3D11_SHADER_RESOURCE_VIEW_DESC srvDesc;
- srvDesc.Format = mShaderResourceFormat;
- srvDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2DARRAY;
- srvDesc.Texture2DArray.MostDetailedMip = mTopLevel + mipLevel;
- srvDesc.Texture2DArray.MipLevels = 1;
- srvDesc.Texture2DArray.FirstArraySlice = layer;
- srvDesc.Texture2DArray.ArraySize = 1;
-
- ID3D11ShaderResourceView *srv;
- result = device->CreateShaderResourceView(texture, &srvDesc, &srv);
-
- ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
- if (FAILED(result))
+ else
{
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal shader resource view for texture storage, result: 0x%X.", result);
+ blitSRV = srv.makeCopy();
}
- d3d11::SetDebugName(srv, "TexStorage2DArray.RenderTargetSRV");
+ srv.setDebugName("TexStorage2DArray.RenderTargetSRV");
- if (mRenderTargetFormat != DXGI_FORMAT_UNKNOWN)
+ if (mFormatInfo.rtvFormat != DXGI_FORMAT_UNKNOWN)
{
D3D11_RENDER_TARGET_VIEW_DESC rtvDesc;
- rtvDesc.Format = mRenderTargetFormat;
- rtvDesc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE2DARRAY;
- rtvDesc.Texture2DArray.MipSlice = mTopLevel + mipLevel;
+ rtvDesc.Format = mFormatInfo.rtvFormat;
+ rtvDesc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE2DARRAY;
+ rtvDesc.Texture2DArray.MipSlice = mTopLevel + mipLevel;
rtvDesc.Texture2DArray.FirstArraySlice = layer;
- rtvDesc.Texture2DArray.ArraySize = 1;
+ rtvDesc.Texture2DArray.ArraySize = numLayers;
- ID3D11RenderTargetView *rtv;
- result = device->CreateRenderTargetView(texture, &rtvDesc, &rtv);
+ d3d11::RenderTargetView rtv;
+ ANGLE_TRY(mRenderer->allocateResource(rtvDesc, texture->get(), &rtv));
+ rtv.setDebugName("TexStorage2DArray.RenderTargetRTV");
- ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
- if (FAILED(result))
- {
- SafeRelease(srv);
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal render target view for texture storage, result: 0x%X.", result);
- }
-
- d3d11::SetDebugName(rtv, "TexStorage2DArray.RenderTargetRTV");
-
- mRenderTargets[key] = new TextureRenderTarget11(rtv, texture, srv, mInternalFormat, getLevelWidth(mipLevel), getLevelHeight(mipLevel), 1, 0);
-
- // RenderTarget will take ownership of these resources
- SafeRelease(rtv);
- SafeRelease(srv);
+ mRenderTargets[key].reset(new TextureRenderTarget11(
+ std::move(rtv), *texture, srv, blitSRV, mFormatInfo.internalFormat, getFormatSet(),
+ getLevelWidth(mipLevel), getLevelHeight(mipLevel), 1, 0));
}
else
{
- UNREACHABLE();
+ ASSERT(mFormatInfo.dsvFormat != DXGI_FORMAT_UNKNOWN);
+
+ D3D11_DEPTH_STENCIL_VIEW_DESC dsvDesc;
+ dsvDesc.Format = mFormatInfo.dsvFormat;
+ dsvDesc.ViewDimension = D3D11_DSV_DIMENSION_TEXTURE2DARRAY;
+ dsvDesc.Texture2DArray.MipSlice = mTopLevel + mipLevel;
+ dsvDesc.Texture2DArray.FirstArraySlice = layer;
+ dsvDesc.Texture2DArray.ArraySize = numLayers;
+ dsvDesc.Flags = 0;
+
+ d3d11::DepthStencilView dsv;
+ ANGLE_TRY(mRenderer->allocateResource(dsvDesc, texture->get(), &dsv));
+ dsv.setDebugName("TexStorage2DArray.RenderTargetDSV");
+
+ mRenderTargets[key].reset(new TextureRenderTarget11(
+ std::move(dsv), *texture, srv, mFormatInfo.internalFormat, getFormatSet(),
+ getLevelWidth(mipLevel), getLevelHeight(mipLevel), 1, 0));
}
}
ASSERT(outRT);
- *outRT = mRenderTargets[key];
- return gl::Error(GL_NO_ERROR);
+ *outRT = mRenderTargets[key].get();
+ return gl::NoError();
}
-gl::Error TextureStorage11_2DArray::getSwizzleTexture(ID3D11Resource **outTexture)
+gl::Error TextureStorage11_2DArray::getSwizzleTexture(const TextureHelper11 **outTexture)
{
- if (!mSwizzleTexture)
+ if (!mSwizzleTexture.valid())
{
- ID3D11Device *device = mRenderer->getDevice();
+ const auto &format = mFormatInfo.getSwizzleFormat(mRenderer->getRenderer11DeviceCaps());
D3D11_TEXTURE2D_DESC desc;
- desc.Width = mTextureWidth;
- desc.Height = mTextureHeight;
- desc.MipLevels = mMipLevels;
- desc.ArraySize = mTextureDepth;
- desc.Format = mSwizzleTextureFormat;
- desc.SampleDesc.Count = 1;
+ desc.Width = mTextureWidth;
+ desc.Height = mTextureHeight;
+ desc.MipLevels = mMipLevels;
+ desc.ArraySize = mTextureDepth;
+ desc.Format = format.texFormat;
+ desc.SampleDesc.Count = 1;
desc.SampleDesc.Quality = 0;
- desc.Usage = D3D11_USAGE_DEFAULT;
- desc.BindFlags = D3D11_BIND_SHADER_RESOURCE | D3D11_BIND_RENDER_TARGET;
- desc.CPUAccessFlags = 0;
- desc.MiscFlags = 0;
-
- HRESULT result = device->CreateTexture2D(&desc, NULL, &mSwizzleTexture);
-
- ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal swizzle texture, result: 0x%X.", result);
- }
+ desc.Usage = D3D11_USAGE_DEFAULT;
+ desc.BindFlags = D3D11_BIND_SHADER_RESOURCE | D3D11_BIND_RENDER_TARGET;
+ desc.CPUAccessFlags = 0;
+ desc.MiscFlags = 0;
- d3d11::SetDebugName(*outTexture, "TexStorage2DArray.SwizzleTexture");
+ ANGLE_TRY(mRenderer->allocateTexture(desc, format, &mSwizzleTexture));
+ mSwizzleTexture.setDebugName("TexStorage2DArray.SwizzleTexture");
}
- *outTexture = mSwizzleTexture;
- return gl::Error(GL_NO_ERROR);
+ *outTexture = &mSwizzleTexture;
+ return gl::NoError();
}
-gl::Error TextureStorage11_2DArray::getSwizzleRenderTarget(int mipLevel, ID3D11RenderTargetView **outRTV)
+gl::Error TextureStorage11_2DArray::getSwizzleRenderTarget(int mipLevel,
+ const d3d11::RenderTargetView **outRTV)
{
ASSERT(mipLevel >= 0 && mipLevel < getLevelCount());
ASSERT(outRTV);
- if (!mSwizzleRenderTargets[mipLevel])
+ if (!mSwizzleRenderTargets[mipLevel].valid())
{
- ID3D11Resource *swizzleTexture = NULL;
- gl::Error error = getSwizzleTexture(&swizzleTexture);
- if (error.isError())
- {
- return error;
- }
-
- ID3D11Device *device = mRenderer->getDevice();
+ const TextureHelper11 *swizzleTexture = nullptr;
+ ANGLE_TRY(getSwizzleTexture(&swizzleTexture));
D3D11_RENDER_TARGET_VIEW_DESC rtvDesc;
- rtvDesc.Format = mSwizzleRenderTargetFormat;
- rtvDesc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE2DARRAY;
- rtvDesc.Texture2DArray.MipSlice = mTopLevel + mipLevel;
+ rtvDesc.Format =
+ mFormatInfo.getSwizzleFormat(mRenderer->getRenderer11DeviceCaps()).rtvFormat;
+ rtvDesc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE2DARRAY;
+ rtvDesc.Texture2DArray.MipSlice = mTopLevel + mipLevel;
rtvDesc.Texture2DArray.FirstArraySlice = 0;
- rtvDesc.Texture2DArray.ArraySize = mTextureDepth;
+ rtvDesc.Texture2DArray.ArraySize = mTextureDepth;
- HRESULT result = device->CreateRenderTargetView(mSwizzleTexture, &rtvDesc, &mSwizzleRenderTargets[mipLevel]);
+ ANGLE_TRY(mRenderer->allocateResource(rtvDesc, mSwizzleTexture.get(),
+ &mSwizzleRenderTargets[mipLevel]));
+ }
- ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal swizzle render target view, result: 0x%X.", result);
- }
+ *outRTV = &mSwizzleRenderTargets[mipLevel];
+ return gl::NoError();
+}
+
+gl::ErrorOrResult<TextureStorage11::DropStencil> TextureStorage11_2DArray::ensureDropStencilTexture(
+ const gl::Context *context)
+{
+ if (mDropStencilTexture.valid())
+ {
+ return DropStencil::ALREADY_EXISTS;
}
- *outRTV = mSwizzleRenderTargets[mipLevel];
- return gl::Error(GL_NO_ERROR);
+ D3D11_TEXTURE2D_DESC dropDesc = {};
+ dropDesc.ArraySize = mTextureDepth;
+ dropDesc.BindFlags = D3D11_BIND_SHADER_RESOURCE | D3D11_BIND_DEPTH_STENCIL;
+ dropDesc.CPUAccessFlags = 0;
+ dropDesc.Format = DXGI_FORMAT_R32_TYPELESS;
+ dropDesc.Height = mTextureHeight;
+ dropDesc.MipLevels = mMipLevels;
+ dropDesc.MiscFlags = 0;
+ dropDesc.SampleDesc.Count = 1;
+ dropDesc.SampleDesc.Quality = 0;
+ dropDesc.Usage = D3D11_USAGE_DEFAULT;
+ dropDesc.Width = mTextureWidth;
+
+ const auto &format =
+ d3d11::Format::Get(GL_DEPTH_COMPONENT32F, mRenderer->getRenderer11DeviceCaps());
+ ANGLE_TRY(mRenderer->allocateTexture(dropDesc, format, &mDropStencilTexture));
+ mDropStencilTexture.setDebugName("TexStorage2DArray.DropStencil");
+
+ std::vector<GLsizei> layerCounts(mMipLevels, mTextureDepth);
+
+ ANGLE_TRY(initDropStencilTexture(
+ context, gl::ImageIndexIterator::Make2DArray(0, mMipLevels, layerCounts.data())));
+
+ return DropStencil::CREATED;
}
+TextureStorage11_2DMultisample::TextureStorage11_2DMultisample(Renderer11 *renderer,
+ GLenum internalformat,
+ GLsizei width,
+ GLsizei height,
+ int levels,
+ int samples,
+ bool fixedSampleLocations)
+ : TextureStorage11(
+ renderer,
+ GetTextureBindFlags(internalformat, renderer->getRenderer11DeviceCaps(), true),
+ GetTextureMiscFlags(internalformat, renderer->getRenderer11DeviceCaps(), true, levels),
+ internalformat),
+ mTexture(),
+ mRenderTarget(nullptr)
+{
+ // adjust size if needed for compressed textures
+ d3d11::MakeValidSize(false, mFormatInfo.texFormat, &width, &height, &mTopLevel);
+
+ mMipLevels = 1;
+ mTextureWidth = width;
+ mTextureHeight = height;
+ mTextureDepth = 1;
+ mSamples = samples;
+ mFixedSampleLocations = fixedSampleLocations;
+}
+
+gl::Error TextureStorage11_2DMultisample::onDestroy(const gl::Context *context)
+{
+ InvalidateRenderTarget(context, mRenderTarget.get());
+ mRenderTarget.reset();
+ return gl::NoError();
}
+
+TextureStorage11_2DMultisample::~TextureStorage11_2DMultisample()
+{
+}
+
+gl::Error TextureStorage11_2DMultisample::copyToStorage(const gl::Context *context,
+ TextureStorage *destStorage)
+{
+ UNIMPLEMENTED();
+ return gl::InternalError() << "copyToStorage is unimplemented";
+}
+
+void TextureStorage11_2DMultisample::associateImage(Image11 *image, const gl::ImageIndex &index)
+{
+}
+
+void TextureStorage11_2DMultisample::verifyAssociatedImageValid(const gl::ImageIndex &index,
+ Image11 *expectedImage)
+{
+}
+
+void TextureStorage11_2DMultisample::disassociateImage(const gl::ImageIndex &index,
+ Image11 *expectedImage)
+{
+}
+
+gl::Error TextureStorage11_2DMultisample::releaseAssociatedImage(const gl::Context *context,
+ const gl::ImageIndex &index,
+ Image11 *incomingImage)
+{
+ return gl::NoError();
+}
+
+gl::Error TextureStorage11_2DMultisample::getResource(const gl::Context *context,
+ const TextureHelper11 **outResource)
+{
+ ANGLE_TRY(ensureTextureExists(1));
+
+ *outResource = &mTexture;
+ return gl::NoError();
+}
+
+gl::Error TextureStorage11_2DMultisample::ensureTextureExists(int mipLevels)
+{
+ // For Multisampled textures, mipLevels always equals 1.
+ ASSERT(mipLevels == 1);
+
+ // if the width or height is not positive this should be treated as an incomplete texture
+ // we handle that here by skipping the d3d texture creation
+ if (!mTexture.valid() && mTextureWidth > 0 && mTextureHeight > 0)
+ {
+ D3D11_TEXTURE2D_DESC desc;
+ ZeroMemory(&desc, sizeof(desc));
+ desc.Width = mTextureWidth; // Compressed texture size constraints?
+ desc.Height = mTextureHeight;
+ desc.MipLevels = mipLevels;
+ desc.ArraySize = 1;
+ desc.Format = mFormatInfo.texFormat;
+ desc.Usage = D3D11_USAGE_DEFAULT;
+ desc.BindFlags = getBindFlags();
+ desc.CPUAccessFlags = 0;
+ desc.MiscFlags = getMiscFlags();
+
+ const gl::TextureCaps &textureCaps =
+ mRenderer->getNativeTextureCaps().get(mFormatInfo.internalFormat);
+ GLuint supportedSamples = textureCaps.getNearestSamples(mSamples);
+ desc.SampleDesc.Count = (supportedSamples == 0) ? 1 : supportedSamples;
+ desc.SampleDesc.Quality = static_cast<UINT>(D3D11_STANDARD_MULTISAMPLE_PATTERN);
+
+ ANGLE_TRY(mRenderer->allocateTexture(desc, mFormatInfo, &mTexture));
+ mTexture.setDebugName("TexStorage2DMS.Texture");
+ }
+
+ return gl::NoError();
+}
+
+gl::Error TextureStorage11_2DMultisample::getRenderTarget(const gl::Context *context,
+ const gl::ImageIndex &index,
+ RenderTargetD3D **outRT)
+{
+ ASSERT(!index.hasLayer());
+
+ const int level = index.mipIndex;
+ ASSERT(level == 0);
+
+ ASSERT(outRT);
+ if (mRenderTarget)
+ {
+ *outRT = mRenderTarget.get();
+ return gl::NoError();
+ }
+
+ const TextureHelper11 *texture = nullptr;
+ ANGLE_TRY(getResource(context, &texture));
+
+ const d3d11::SharedSRV *srv = nullptr;
+ ANGLE_TRY(getSRVLevel(context, level, false, &srv));
+
+ const d3d11::SharedSRV *blitSRV = nullptr;
+ ANGLE_TRY(getSRVLevel(context, level, true, &blitSRV));
+
+ if (mFormatInfo.rtvFormat != DXGI_FORMAT_UNKNOWN)
+ {
+ D3D11_RENDER_TARGET_VIEW_DESC rtvDesc;
+ rtvDesc.Format = mFormatInfo.rtvFormat;
+ rtvDesc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE2DMS;
+
+ d3d11::RenderTargetView rtv;
+ ANGLE_TRY(mRenderer->allocateResource(rtvDesc, texture->get(), &rtv));
+
+ mRenderTarget.reset(new TextureRenderTarget11(
+ std::move(rtv), *texture, *srv, *blitSRV, mFormatInfo.internalFormat, getFormatSet(),
+ getLevelWidth(level), getLevelHeight(level), 1, mSamples));
+
+ *outRT = mRenderTarget.get();
+ return gl::NoError();
+ }
+
+ ASSERT(mFormatInfo.dsvFormat != DXGI_FORMAT_UNKNOWN);
+
+ D3D11_DEPTH_STENCIL_VIEW_DESC dsvDesc;
+ dsvDesc.Format = mFormatInfo.dsvFormat;
+ dsvDesc.ViewDimension = D3D11_DSV_DIMENSION_TEXTURE2DMS;
+ dsvDesc.Flags = 0;
+
+ d3d11::DepthStencilView dsv;
+ ANGLE_TRY(mRenderer->allocateResource(dsvDesc, texture->get(), &dsv));
+
+ mRenderTarget.reset(new TextureRenderTarget11(
+ std::move(dsv), *texture, *srv, mFormatInfo.internalFormat, getFormatSet(),
+ getLevelWidth(level), getLevelHeight(level), 1, mSamples));
+
+ *outRT = mRenderTarget.get();
+ return gl::NoError();
+}
+
+gl::Error TextureStorage11_2DMultisample::createSRV(const gl::Context *context,
+ int baseLevel,
+ int mipLevels,
+ DXGI_FORMAT format,
+ const TextureHelper11 &texture,
+ d3d11::SharedSRV *outSRV)
+{
+ ASSERT(outSRV);
+
+ D3D11_SHADER_RESOURCE_VIEW_DESC srvDesc;
+ srvDesc.Format = format;
+ srvDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2DMS;
+
+ ANGLE_TRY(mRenderer->allocateResource(srvDesc, texture.get(), outSRV));
+ outSRV->setDebugName("TexStorage2DMS.SRV");
+ return gl::NoError();
+}
+
+gl::Error TextureStorage11_2DMultisample::getSwizzleTexture(const TextureHelper11 **outTexture)
+{
+ UNIMPLEMENTED();
+ return gl::InternalError() << "getSwizzleTexture is unimplemented.";
+}
+
+gl::Error TextureStorage11_2DMultisample::getSwizzleRenderTarget(
+ int mipLevel,
+ const d3d11::RenderTargetView **outRTV)
+{
+ UNIMPLEMENTED();
+ return gl::InternalError() << "getSwizzleRenderTarget is unimplemented.";
+}
+
+gl::ErrorOrResult<TextureStorage11::DropStencil>
+TextureStorage11_2DMultisample::ensureDropStencilTexture(const gl::Context *context)
+{
+ UNIMPLEMENTED();
+ return gl::InternalError() << "Drop stencil texture not implemented.";
+}
+
+} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/TextureStorage11.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/TextureStorage11.h
index a88db2f0af..336aa495a8 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/TextureStorage11.h
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/TextureStorage11.h
@@ -10,10 +10,13 @@
#ifndef LIBANGLE_RENDERER_D3D_D3D11_TEXTURESTORAGE11_H_
#define LIBANGLE_RENDERER_D3D_D3D11_TEXTURESTORAGE11_H_
-#include "libANGLE/Texture.h"
#include "libANGLE/Error.h"
+#include "libANGLE/Texture.h"
#include "libANGLE/renderer/d3d/TextureStorage.h"
+#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
+#include "libANGLE/renderer/d3d/d3d11/texture_format_table.h"
+#include <array>
#include <map>
namespace gl
@@ -31,69 +34,111 @@ class SwapChain11;
class Image11;
struct Renderer11DeviceCaps;
+template <typename T>
+using TexLevelArray = std::array<T, gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS>;
+
+template <typename T>
+using CubeFaceArray = std::array<T, gl::CUBE_FACE_COUNT>;
+
class TextureStorage11 : public TextureStorage
{
public:
- virtual ~TextureStorage11();
+ ~TextureStorage11() override;
static DWORD GetTextureBindFlags(GLenum internalFormat, const Renderer11DeviceCaps &renderer11DeviceCaps, bool renderTarget);
static DWORD GetTextureMiscFlags(GLenum internalFormat, const Renderer11DeviceCaps &renderer11DeviceCaps, bool renderTarget, int levels);
UINT getBindFlags() const;
UINT getMiscFlags() const;
-
- virtual gl::Error getResource(ID3D11Resource **outResource) = 0;
- virtual gl::Error getSRV(const gl::TextureState &textureState,
- ID3D11ShaderResourceView **outSRV);
- virtual gl::Error getRenderTarget(const gl::ImageIndex &index, RenderTargetD3D **outRT) = 0;
-
- virtual gl::Error generateMipmap(const gl::ImageIndex &sourceIndex, const gl::ImageIndex &destIndex);
-
- virtual int getTopLevel() const;
- virtual bool isRenderTarget() const;
- virtual bool isManaged() const;
+ const d3d11::Format &getFormatSet() const;
+ gl::Error getSRVLevels(const gl::Context *context,
+ GLint baseLevel,
+ GLint maxLevel,
+ const d3d11::SharedSRV **outSRV);
+ gl::Error generateSwizzles(const gl::Context *context, const gl::SwizzleState &swizzleTarget);
+ void markLevelDirty(int mipLevel);
+ void markDirty();
+
+ gl::Error updateSubresourceLevel(const gl::Context *context,
+ const TextureHelper11 &texture,
+ unsigned int sourceSubresource,
+ const gl::ImageIndex &index,
+ const gl::Box &copyArea);
+
+ gl::Error copySubresourceLevel(const gl::Context *context,
+ const TextureHelper11 &dstTexture,
+ unsigned int dstSubresource,
+ const gl::ImageIndex &index,
+ const gl::Box &region);
+
+ // TextureStorage virtual functions
+ int getTopLevel() const override;
+ bool isRenderTarget() const override;
+ bool isManaged() const override;
bool supportsNativeMipmapFunction() const override;
- virtual int getLevelCount() const;
+ int getLevelCount() const override;
+ gl::Error generateMipmap(const gl::Context *context,
+ const gl::ImageIndex &sourceIndex,
+ const gl::ImageIndex &destIndex) override;
+ gl::Error copyToStorage(const gl::Context *context, TextureStorage *destStorage) override;
+ gl::Error setData(const gl::Context *context,
+ const gl::ImageIndex &index,
+ ImageD3D *image,
+ const gl::Box *destBox,
+ GLenum type,
+ const gl::PixelUnpackState &unpack,
+ const uint8_t *pixelData) override;
+
+ virtual gl::Error getSRV(const gl::Context *context,
+ const gl::TextureState &textureState,
+ const d3d11::SharedSRV **outSRV);
virtual UINT getSubresourceIndex(const gl::ImageIndex &index) const;
-
- gl::Error generateSwizzles(GLenum swizzleRed, GLenum swizzleGreen, GLenum swizzleBlue, GLenum swizzleAlpha);
- void invalidateSwizzleCacheLevel(int mipLevel);
- void invalidateSwizzleCache();
-
- gl::Error updateSubresourceLevel(ID3D11Resource *texture, unsigned int sourceSubresource,
- const gl::ImageIndex &index, const gl::Box &copyArea);
-
- gl::Error copySubresourceLevel(ID3D11Resource* dstTexture, unsigned int dstSubresource,
- const gl::ImageIndex &index, const gl::Box &region);
-
+ virtual gl::Error getResource(const gl::Context *context,
+ const TextureHelper11 **outResource) = 0;
virtual void associateImage(Image11* image, const gl::ImageIndex &index) = 0;
virtual void disassociateImage(const gl::ImageIndex &index, Image11* expectedImage) = 0;
- virtual bool isAssociatedImageValid(const gl::ImageIndex &index, Image11* expectedImage) = 0;
- virtual gl::Error releaseAssociatedImage(const gl::ImageIndex &index, Image11* incomingImage) = 0;
-
- virtual gl::Error copyToStorage(TextureStorage *destStorage);
- virtual gl::Error setData(const gl::ImageIndex &index, ImageD3D *image, const gl::Box *destBox, GLenum type,
- const gl::PixelUnpackState &unpack, const uint8_t *pixelData);
-
- gl::Error getSRVLevels(GLint baseLevel, GLint maxLevel, ID3D11ShaderResourceView **outSRV);
+ virtual void verifyAssociatedImageValid(const gl::ImageIndex &index,
+ Image11 *expectedImage) = 0;
+ virtual gl::Error releaseAssociatedImage(const gl::Context *context,
+ const gl::ImageIndex &index,
+ Image11 *incomingImage) = 0;
protected:
- TextureStorage11(Renderer11 *renderer, UINT bindFlags, UINT miscFlags);
+ TextureStorage11(Renderer11 *renderer, UINT bindFlags, UINT miscFlags, GLenum internalFormat);
int getLevelWidth(int mipLevel) const;
int getLevelHeight(int mipLevel) const;
int getLevelDepth(int mipLevel) const;
// Some classes (e.g. TextureStorage11_2D) will override getMippedResource.
- virtual gl::Error getMippedResource(ID3D11Resource **outResource) { return getResource(outResource); }
-
- virtual gl::Error getSwizzleTexture(ID3D11Resource **outTexture) = 0;
- virtual gl::Error getSwizzleRenderTarget(int mipLevel, ID3D11RenderTargetView **outRTV) = 0;
- gl::Error getSRVLevel(int mipLevel, ID3D11ShaderResourceView **outSRV);
+ virtual gl::Error getMippedResource(const gl::Context *context,
+ const TextureHelper11 **outResource);
+
+ virtual gl::Error getSwizzleTexture(const TextureHelper11 **outTexture) = 0;
+ virtual gl::Error getSwizzleRenderTarget(int mipLevel,
+ const d3d11::RenderTargetView **outRTV) = 0;
+ gl::Error getSRVLevel(const gl::Context *context,
+ int mipLevel,
+ bool blitSRV,
+ const d3d11::SharedSRV **outSRV);
+
+ // Get a version of a depth texture with only depth information, not stencil.
+ enum DropStencil
+ {
+ CREATED,
+ ALREADY_EXISTS
+ };
+ virtual gl::ErrorOrResult<DropStencil> ensureDropStencilTexture(const gl::Context *context);
+ gl::Error initDropStencilTexture(const gl::Context *context, const gl::ImageIndexIterator &it);
- virtual gl::Error createSRV(int baseLevel, int mipLevels, DXGI_FORMAT format, ID3D11Resource *texture,
- ID3D11ShaderResourceView **outSRV) const = 0;
+ // The baseLevel parameter should *not* have mTopLevel applied.
+ virtual gl::Error createSRV(const gl::Context *context,
+ int baseLevel,
+ int mipLevels,
+ DXGI_FORMAT format,
+ const TextureHelper11 &texture,
+ d3d11::SharedSRV *outSRV) = 0;
- void verifySwizzleExists(GLenum swizzleRed, GLenum swizzleGreen, GLenum swizzleBlue, GLenum swizzleAlpha);
+ void verifySwizzleExists(const gl::SwizzleState &swizzleState);
// Clear all cached non-swizzle SRVs and invalidate the swizzle cache.
void clearSRVCache();
@@ -102,32 +147,13 @@ class TextureStorage11 : public TextureStorage
int mTopLevel;
unsigned int mMipLevels;
- GLenum mInternalFormat;
- DXGI_FORMAT mTextureFormat;
- DXGI_FORMAT mShaderResourceFormat;
- DXGI_FORMAT mRenderTargetFormat;
- DXGI_FORMAT mDepthStencilFormat;
- DXGI_FORMAT mSwizzleTextureFormat;
- DXGI_FORMAT mSwizzleShaderResourceFormat;
- DXGI_FORMAT mSwizzleRenderTargetFormat;
+ const d3d11::Format &mFormatInfo;
unsigned int mTextureWidth;
unsigned int mTextureHeight;
unsigned int mTextureDepth;
- struct SwizzleCacheValue
- {
- GLenum swizzleRed;
- GLenum swizzleGreen;
- GLenum swizzleBlue;
- GLenum swizzleAlpha;
-
- SwizzleCacheValue();
- SwizzleCacheValue(GLenum red, GLenum green, GLenum blue, GLenum alpha);
-
- bool operator ==(const SwizzleCacheValue &other) const;
- bool operator !=(const SwizzleCacheValue &other) const;
- };
- SwizzleCacheValue mSwizzleCache[gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS];
+ TexLevelArray<gl::SwizzleState> mSwizzleCache;
+ TextureHelper11 mDropStencilTexture;
private:
const UINT mBindFlags;
@@ -135,18 +161,24 @@ class TextureStorage11 : public TextureStorage
struct SRVKey
{
- SRVKey(int baseLevel = 0, int mipLevels = 0, bool swizzle = false);
+ SRVKey(int baseLevel, int mipLevels, bool swizzle, bool dropStencil);
bool operator<(const SRVKey &rhs) const;
- int baseLevel;
- int mipLevels;
- bool swizzle;
+ int baseLevel = 0; // Without mTopLevel applied.
+ int mipLevels = 0;
+ bool swizzle = false;
+ bool dropStencil = false;
};
- typedef std::map<SRVKey, ID3D11ShaderResourceView *> SRVCache;
+ typedef std::map<SRVKey, d3d11::SharedSRV> SRVCache;
+
+ gl::Error getCachedOrCreateSRV(const gl::Context *context,
+ const SRVKey &key,
+ const d3d11::SharedSRV **outSRV);
SRVCache mSrvCache;
- ID3D11ShaderResourceView *mLevelSRVs[gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS];
+ TexLevelArray<d3d11::SharedSRV> mLevelSRVs;
+ TexLevelArray<d3d11::SharedSRV> mLevelBlitSRVs;
};
class TextureStorage11_2D : public TextureStorage11
@@ -154,33 +186,48 @@ class TextureStorage11_2D : public TextureStorage11
public:
TextureStorage11_2D(Renderer11 *renderer, SwapChain11 *swapchain);
TextureStorage11_2D(Renderer11 *renderer, GLenum internalformat, bool renderTarget, GLsizei width, GLsizei height, int levels, bool hintLevelZeroOnly = false);
- virtual ~TextureStorage11_2D();
+ ~TextureStorage11_2D() override;
- virtual gl::Error getResource(ID3D11Resource **outResource);
- virtual gl::Error getMippedResource(ID3D11Resource **outResource);
- virtual gl::Error getRenderTarget(const gl::ImageIndex &index, RenderTargetD3D **outRT);
+ gl::Error onDestroy(const gl::Context *context) override;
- virtual gl::Error copyToStorage(TextureStorage *destStorage);
+ gl::Error getResource(const gl::Context *context, const TextureHelper11 **outResource) override;
+ gl::Error getMippedResource(const gl::Context *context,
+ const TextureHelper11 **outResource) override;
+ gl::Error getRenderTarget(const gl::Context *context,
+ const gl::ImageIndex &index,
+ RenderTargetD3D **outRT) override;
- virtual void associateImage(Image11* image, const gl::ImageIndex &index);
- virtual void disassociateImage(const gl::ImageIndex &index, Image11* expectedImage);
- virtual bool isAssociatedImageValid(const gl::ImageIndex &index, Image11* expectedImage);
- virtual gl::Error releaseAssociatedImage(const gl::ImageIndex &index, Image11* incomingImage);
+ gl::Error copyToStorage(const gl::Context *context, TextureStorage *destStorage) override;
- virtual gl::Error useLevelZeroWorkaroundTexture(bool useLevelZeroTexture);
+ void associateImage(Image11 *image, const gl::ImageIndex &index) override;
+ void disassociateImage(const gl::ImageIndex &index, Image11 *expectedImage) override;
+ void verifyAssociatedImageValid(const gl::ImageIndex &index, Image11 *expectedImage) override;
+ gl::Error releaseAssociatedImage(const gl::Context *context,
+ const gl::ImageIndex &index,
+ Image11 *incomingImage) override;
+
+ gl::Error useLevelZeroWorkaroundTexture(const gl::Context *context,
+ bool useLevelZeroTexture) override;
protected:
- virtual gl::Error getSwizzleTexture(ID3D11Resource **outTexture);
- virtual gl::Error getSwizzleRenderTarget(int mipLevel, ID3D11RenderTargetView **outRTV);
+ gl::Error getSwizzleTexture(const TextureHelper11 **outTexture) override;
+ gl::Error getSwizzleRenderTarget(int mipLevel, const d3d11::RenderTargetView **outRTV) override;
+
+ gl::ErrorOrResult<DropStencil> ensureDropStencilTexture(const gl::Context *context) override;
gl::Error ensureTextureExists(int mipLevels);
private:
- virtual gl::Error createSRV(int baseLevel, int mipLevels, DXGI_FORMAT format, ID3D11Resource *texture,
- ID3D11ShaderResourceView **outSRV) const;
+ gl::Error createSRV(const gl::Context *context,
+ int baseLevel,
+ int mipLevels,
+ DXGI_FORMAT format,
+ const TextureHelper11 &texture,
+ d3d11::SharedSRV *outSRV) override;
- ID3D11Texture2D *mTexture;
- RenderTarget11 *mRenderTarget[gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS];
+ TextureHelper11 mTexture;
+ TexLevelArray<std::unique_ptr<RenderTarget11>> mRenderTarget;
+ bool mHasKeyedMutex;
// These are members related to the zero max-LOD workaround.
// D3D11 Feature Level 9_3 can't disable mipmaps on a mipmapped texture (i.e. solely sample from level zero).
@@ -191,108 +238,179 @@ class TextureStorage11_2D : public TextureStorage11
// One example of this is an application that creates a texture, calls glGenerateMipmap, and then disables mipmaps on the texture.
// A more likely example is an app that creates an empty texture, renders to it, and then calls glGenerateMipmap
// TODO: In this rendering scenario, release the mLevelZeroTexture after mTexture has been created to save memory.
- ID3D11Texture2D *mLevelZeroTexture;
- RenderTarget11 *mLevelZeroRenderTarget;
+ TextureHelper11 mLevelZeroTexture;
+ std::unique_ptr<RenderTarget11> mLevelZeroRenderTarget;
bool mUseLevelZeroTexture;
// Swizzle-related variables
- ID3D11Texture2D *mSwizzleTexture;
- ID3D11RenderTargetView *mSwizzleRenderTargets[gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS];
+ TextureHelper11 mSwizzleTexture;
+ TexLevelArray<d3d11::RenderTargetView> mSwizzleRenderTargets;
+
+ TexLevelArray<Image11 *> mAssociatedImages;
+};
+
+class TextureStorage11_External : public TextureStorage11
+{
+ public:
+ TextureStorage11_External(Renderer11 *renderer,
+ egl::Stream *stream,
+ const egl::Stream::GLTextureDescription &glDesc);
+ ~TextureStorage11_External() override;
+
+ gl::Error onDestroy(const gl::Context *context) override;
+
+ gl::Error getResource(const gl::Context *context, const TextureHelper11 **outResource) override;
+ gl::Error getMippedResource(const gl::Context *context,
+ const TextureHelper11 **outResource) override;
+ gl::Error getRenderTarget(const gl::Context *context,
+ const gl::ImageIndex &index,
+ RenderTargetD3D **outRT) override;
+
+ gl::Error copyToStorage(const gl::Context *context, TextureStorage *destStorage) override;
+
+ void associateImage(Image11 *image, const gl::ImageIndex &index) override;
+ void disassociateImage(const gl::ImageIndex &index, Image11 *expectedImage) override;
+ void verifyAssociatedImageValid(const gl::ImageIndex &index, Image11 *expectedImage) override;
+ gl::Error releaseAssociatedImage(const gl::Context *context,
+ const gl::ImageIndex &index,
+ Image11 *incomingImage) override;
+
+ protected:
+ gl::Error getSwizzleTexture(const TextureHelper11 **outTexture) override;
+ gl::Error getSwizzleRenderTarget(int mipLevel, const d3d11::RenderTargetView **outRTV) override;
+
+ private:
+ gl::Error createSRV(const gl::Context *context,
+ int baseLevel,
+ int mipLevels,
+ DXGI_FORMAT format,
+ const TextureHelper11 &texture,
+ d3d11::SharedSRV *outSRV) override;
+
+ TextureHelper11 mTexture;
+ int mSubresourceIndex;
+ bool mHasKeyedMutex;
- Image11 *mAssociatedImages[gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS];
+ Image11 *mAssociatedImage;
};
class TextureStorage11_EGLImage final : public TextureStorage11
{
public:
- TextureStorage11_EGLImage(Renderer11 *renderer, EGLImageD3D *eglImage);
+ TextureStorage11_EGLImage(Renderer11 *renderer,
+ EGLImageD3D *eglImage,
+ RenderTarget11 *renderTarget11);
~TextureStorage11_EGLImage() override;
- gl::Error getResource(ID3D11Resource **outResource) override;
- gl::Error getSRV(const gl::TextureState &textureState,
- ID3D11ShaderResourceView **outSRV) override;
- gl::Error getMippedResource(ID3D11Resource **outResource) override;
- gl::Error getRenderTarget(const gl::ImageIndex &index, RenderTargetD3D **outRT) override;
+ gl::Error getResource(const gl::Context *context, const TextureHelper11 **outResource) override;
+ gl::Error getSRV(const gl::Context *context,
+ const gl::TextureState &textureState,
+ const d3d11::SharedSRV **outSRV) override;
+ gl::Error getMippedResource(const gl::Context *context,
+ const TextureHelper11 **outResource) override;
+ gl::Error getRenderTarget(const gl::Context *context,
+ const gl::ImageIndex &index,
+ RenderTargetD3D **outRT) override;
- gl::Error copyToStorage(TextureStorage *destStorage) override;
+ gl::Error copyToStorage(const gl::Context *context, TextureStorage *destStorage) override;
void associateImage(Image11 *image, const gl::ImageIndex &index) override;
void disassociateImage(const gl::ImageIndex &index, Image11 *expectedImage) override;
- bool isAssociatedImageValid(const gl::ImageIndex &index, Image11 *expectedImage) override;
- gl::Error releaseAssociatedImage(const gl::ImageIndex &index, Image11 *incomingImage) override;
+ void verifyAssociatedImageValid(const gl::ImageIndex &index, Image11 *expectedImage) override;
+ gl::Error releaseAssociatedImage(const gl::Context *context,
+ const gl::ImageIndex &index,
+ Image11 *incomingImage) override;
- gl::Error useLevelZeroWorkaroundTexture(bool useLevelZeroTexture) override;
+ gl::Error useLevelZeroWorkaroundTexture(const gl::Context *context,
+ bool useLevelZeroTexture) override;
protected:
- gl::Error getSwizzleTexture(ID3D11Resource **outTexture) override;
- gl::Error getSwizzleRenderTarget(int mipLevel, ID3D11RenderTargetView **outRTV) override;
+ gl::Error getSwizzleTexture(const TextureHelper11 **outTexture) override;
+ gl::Error getSwizzleRenderTarget(int mipLevel, const d3d11::RenderTargetView **outRTV) override;
private:
// Check if the EGL image's render target has been updated due to orphaning and delete
// any SRVs and other resources based on the image's old render target.
- gl::Error checkForUpdatedRenderTarget();
+ gl::Error checkForUpdatedRenderTarget(const gl::Context *context);
- gl::Error createSRV(int baseLevel,
+ gl::Error createSRV(const gl::Context *context,
+ int baseLevel,
int mipLevels,
DXGI_FORMAT format,
- ID3D11Resource *texture,
- ID3D11ShaderResourceView **outSRV) const override;
+ const TextureHelper11 &texture,
+ d3d11::SharedSRV *outSRV) override;
- gl::Error getImageRenderTarget(RenderTarget11 **outRT) const;
+ gl::Error getImageRenderTarget(const gl::Context *context, RenderTarget11 **outRT) const;
EGLImageD3D *mImage;
uintptr_t mCurrentRenderTarget;
// Swizzle-related variables
- ID3D11Texture2D *mSwizzleTexture;
- std::vector<ID3D11RenderTargetView *> mSwizzleRenderTargets;
+ TextureHelper11 mSwizzleTexture;
+ std::vector<d3d11::RenderTargetView> mSwizzleRenderTargets;
};
class TextureStorage11_Cube : public TextureStorage11
{
public:
TextureStorage11_Cube(Renderer11 *renderer, GLenum internalformat, bool renderTarget, int size, int levels, bool hintLevelZeroOnly);
- virtual ~TextureStorage11_Cube();
+ ~TextureStorage11_Cube() override;
- virtual UINT getSubresourceIndex(const gl::ImageIndex &index) const;
+ gl::Error onDestroy(const gl::Context *context) override;
+
+ UINT getSubresourceIndex(const gl::ImageIndex &index) const override;
- virtual gl::Error getResource(ID3D11Resource **outResource);
- virtual gl::Error getMippedResource(ID3D11Resource **outResource);
- virtual gl::Error getRenderTarget(const gl::ImageIndex &index, RenderTargetD3D **outRT);
+ gl::Error getResource(const gl::Context *context, const TextureHelper11 **outResource) override;
+ gl::Error getMippedResource(const gl::Context *context,
+ const TextureHelper11 **outResource) override;
+ gl::Error getRenderTarget(const gl::Context *context,
+ const gl::ImageIndex &index,
+ RenderTargetD3D **outRT) override;
- virtual gl::Error copyToStorage(TextureStorage *destStorage);
+ gl::Error copyToStorage(const gl::Context *context, TextureStorage *destStorage) override;
- virtual void associateImage(Image11* image, const gl::ImageIndex &index);
- virtual void disassociateImage(const gl::ImageIndex &index, Image11* expectedImage);
- virtual bool isAssociatedImageValid(const gl::ImageIndex &index, Image11* expectedImage);
- virtual gl::Error releaseAssociatedImage(const gl::ImageIndex &index, Image11* incomingImage);
+ void associateImage(Image11 *image, const gl::ImageIndex &index) override;
+ void disassociateImage(const gl::ImageIndex &index, Image11 *expectedImage) override;
+ void verifyAssociatedImageValid(const gl::ImageIndex &index, Image11 *expectedImage) override;
+ gl::Error releaseAssociatedImage(const gl::Context *context,
+ const gl::ImageIndex &index,
+ Image11 *incomingImage) override;
- virtual gl::Error useLevelZeroWorkaroundTexture(bool useLevelZeroTexture);
+ gl::Error useLevelZeroWorkaroundTexture(const gl::Context *context,
+ bool useLevelZeroTexture) override;
protected:
- virtual gl::Error getSwizzleTexture(ID3D11Resource **outTexture);
- virtual gl::Error getSwizzleRenderTarget(int mipLevel, ID3D11RenderTargetView **outRTV);
+ gl::Error getSwizzleTexture(const TextureHelper11 **outTexture) override;
+ gl::Error getSwizzleRenderTarget(int mipLevel, const d3d11::RenderTargetView **outRTV) override;
+
+ gl::ErrorOrResult<DropStencil> ensureDropStencilTexture(const gl::Context *context) override;
gl::Error ensureTextureExists(int mipLevels);
private:
- virtual gl::Error createSRV(int baseLevel, int mipLevels, DXGI_FORMAT format, ID3D11Resource *texture,
- ID3D11ShaderResourceView **outSRV) const;
-
- static const size_t CUBE_FACE_COUNT = 6;
+ gl::Error createSRV(const gl::Context *context,
+ int baseLevel,
+ int mipLevels,
+ DXGI_FORMAT format,
+ const TextureHelper11 &texture,
+ d3d11::SharedSRV *outSRV) override;
+ gl::Error createRenderTargetSRV(const TextureHelper11 &texture,
+ const gl::ImageIndex &index,
+ DXGI_FORMAT resourceFormat,
+ d3d11::SharedSRV *srv) const;
- ID3D11Texture2D *mTexture;
- RenderTarget11 *mRenderTarget[CUBE_FACE_COUNT][gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS];
+ TextureHelper11 mTexture;
+ CubeFaceArray<TexLevelArray<std::unique_ptr<RenderTarget11>>> mRenderTarget;
// Level-zero workaround members. See TextureStorage11_2D's workaround members for a description.
- ID3D11Texture2D *mLevelZeroTexture;
- RenderTarget11 *mLevelZeroRenderTarget[CUBE_FACE_COUNT];
+ TextureHelper11 mLevelZeroTexture;
+ CubeFaceArray<std::unique_ptr<RenderTarget11>> mLevelZeroRenderTarget;
bool mUseLevelZeroTexture;
- ID3D11Texture2D *mSwizzleTexture;
- ID3D11RenderTargetView *mSwizzleRenderTargets[gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS];
+ TextureHelper11 mSwizzleTexture;
+ TexLevelArray<d3d11::RenderTargetView> mSwizzleRenderTargets;
- Image11 *mAssociatedImages[CUBE_FACE_COUNT][gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS];
+ CubeFaceArray<TexLevelArray<Image11 *>> mAssociatedImages;
};
class TextureStorage11_3D : public TextureStorage11
@@ -300,37 +418,46 @@ class TextureStorage11_3D : public TextureStorage11
public:
TextureStorage11_3D(Renderer11 *renderer, GLenum internalformat, bool renderTarget,
GLsizei width, GLsizei height, GLsizei depth, int levels);
- virtual ~TextureStorage11_3D();
+ ~TextureStorage11_3D() override;
+
+ gl::Error onDestroy(const gl::Context *context) override;
- virtual gl::Error getResource(ID3D11Resource **outResource);
+ gl::Error getResource(const gl::Context *context, const TextureHelper11 **outResource) override;
// Handles both layer and non-layer RTs
- virtual gl::Error getRenderTarget(const gl::ImageIndex &index, RenderTargetD3D **outRT);
+ gl::Error getRenderTarget(const gl::Context *context,
+ const gl::ImageIndex &index,
+ RenderTargetD3D **outRT) override;
- virtual void associateImage(Image11* image, const gl::ImageIndex &index);
- virtual void disassociateImage(const gl::ImageIndex &index, Image11* expectedImage);
- virtual bool isAssociatedImageValid(const gl::ImageIndex &index, Image11* expectedImage);
- virtual gl::Error releaseAssociatedImage(const gl::ImageIndex &index, Image11* incomingImage);
+ void associateImage(Image11 *image, const gl::ImageIndex &index) override;
+ void disassociateImage(const gl::ImageIndex &index, Image11 *expectedImage) override;
+ void verifyAssociatedImageValid(const gl::ImageIndex &index, Image11 *expectedImage) override;
+ gl::Error releaseAssociatedImage(const gl::Context *context,
+ const gl::ImageIndex &index,
+ Image11 *incomingImage) override;
protected:
- virtual gl::Error getSwizzleTexture(ID3D11Resource **outTexture);
- virtual gl::Error getSwizzleRenderTarget(int mipLevel, ID3D11RenderTargetView **outRTV);
+ gl::Error getSwizzleTexture(const TextureHelper11 **outTexture) override;
+ gl::Error getSwizzleRenderTarget(int mipLevel, const d3d11::RenderTargetView **outRTV) override;
private:
- virtual gl::Error createSRV(int baseLevel, int mipLevels, DXGI_FORMAT format, ID3D11Resource *texture,
- ID3D11ShaderResourceView **outSRV) const;
+ gl::Error createSRV(const gl::Context *context,
+ int baseLevel,
+ int mipLevels,
+ DXGI_FORMAT format,
+ const TextureHelper11 &texture,
+ d3d11::SharedSRV *outSRV) override;
typedef std::pair<int, int> LevelLayerKey;
- typedef std::map<LevelLayerKey, RenderTarget11*> RenderTargetMap;
- RenderTargetMap mLevelLayerRenderTargets;
+ std::map<LevelLayerKey, std::unique_ptr<RenderTarget11>> mLevelLayerRenderTargets;
- RenderTarget11 *mLevelRenderTargets[gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS];
+ TexLevelArray<std::unique_ptr<RenderTarget11>> mLevelRenderTargets;
- ID3D11Texture3D *mTexture;
- ID3D11Texture3D *mSwizzleTexture;
- ID3D11RenderTargetView *mSwizzleRenderTargets[gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS];
+ TextureHelper11 mTexture;
+ TextureHelper11 mSwizzleTexture;
+ TexLevelArray<d3d11::RenderTargetView> mSwizzleRenderTargets;
- Image11 *mAssociatedImages[gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS];
+ TexLevelArray<Image11 *> mAssociatedImages;
};
class TextureStorage11_2DArray : public TextureStorage11
@@ -338,37 +465,125 @@ class TextureStorage11_2DArray : public TextureStorage11
public:
TextureStorage11_2DArray(Renderer11 *renderer, GLenum internalformat, bool renderTarget,
GLsizei width, GLsizei height, GLsizei depth, int levels);
- virtual ~TextureStorage11_2DArray();
+ ~TextureStorage11_2DArray() override;
+
+ gl::Error onDestroy(const gl::Context *context) override;
- virtual gl::Error getResource(ID3D11Resource **outResource);
- virtual gl::Error getRenderTarget(const gl::ImageIndex &index, RenderTargetD3D **outRT);
+ gl::Error getResource(const gl::Context *context, const TextureHelper11 **outResource) override;
+ gl::Error getRenderTarget(const gl::Context *context,
+ const gl::ImageIndex &index,
+ RenderTargetD3D **outRT) override;
- virtual void associateImage(Image11* image, const gl::ImageIndex &index);
- virtual void disassociateImage(const gl::ImageIndex &index, Image11* expectedImage);
- virtual bool isAssociatedImageValid(const gl::ImageIndex &index, Image11* expectedImage);
- virtual gl::Error releaseAssociatedImage(const gl::ImageIndex &index, Image11* incomingImage);
+ void associateImage(Image11 *image, const gl::ImageIndex &index) override;
+ void disassociateImage(const gl::ImageIndex &index, Image11 *expectedImage) override;
+ void verifyAssociatedImageValid(const gl::ImageIndex &index, Image11 *expectedImage) override;
+ gl::Error releaseAssociatedImage(const gl::Context *context,
+ const gl::ImageIndex &index,
+ Image11 *incomingImage) override;
protected:
- virtual gl::Error getSwizzleTexture(ID3D11Resource **outTexture);
- virtual gl::Error getSwizzleRenderTarget(int mipLevel, ID3D11RenderTargetView **outRTV);
+ gl::Error getSwizzleTexture(const TextureHelper11 **outTexture) override;
+ gl::Error getSwizzleRenderTarget(int mipLevel, const d3d11::RenderTargetView **outRTV) override;
+
+ gl::ErrorOrResult<DropStencil> ensureDropStencilTexture(const gl::Context *context) override;
private:
- virtual gl::Error createSRV(int baseLevel, int mipLevels, DXGI_FORMAT format, ID3D11Resource *texture,
- ID3D11ShaderResourceView **outSRV) const;
+ struct LevelLayerRangeKey
+ {
+ LevelLayerRangeKey(int mipLevelIn, int layerIn, int numLayersIn)
+ : mipLevel(mipLevelIn), layer(layerIn), numLayers(numLayersIn)
+ {
+ }
+ bool operator<(const LevelLayerRangeKey &other) const
+ {
+ if (mipLevel != other.mipLevel)
+ {
+ return mipLevel < other.mipLevel;
+ }
+ if (layer != other.layer)
+ {
+ return layer < other.layer;
+ }
+ return numLayers < other.numLayers;
+ }
+ int mipLevel;
+ int layer;
+ int numLayers;
+ };
- typedef std::pair<int, int> LevelLayerKey;
- typedef std::map<LevelLayerKey, RenderTarget11*> RenderTargetMap;
- RenderTargetMap mRenderTargets;
+ private:
+ gl::Error createSRV(const gl::Context *context,
+ int baseLevel,
+ int mipLevels,
+ DXGI_FORMAT format,
+ const TextureHelper11 &texture,
+ d3d11::SharedSRV *outSRV) override;
+ gl::Error createRenderTargetSRV(const TextureHelper11 &texture,
+ const gl::ImageIndex &index,
+ DXGI_FORMAT resourceFormat,
+ d3d11::SharedSRV *srv) const;
+
+ std::map<LevelLayerRangeKey, std::unique_ptr<RenderTarget11>> mRenderTargets;
- ID3D11Texture2D *mTexture;
+ TextureHelper11 mTexture;
- ID3D11Texture2D *mSwizzleTexture;
- ID3D11RenderTargetView *mSwizzleRenderTargets[gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS];
+ TextureHelper11 mSwizzleTexture;
+ TexLevelArray<d3d11::RenderTargetView> mSwizzleRenderTargets;
- typedef std::map<LevelLayerKey, Image11*> ImageMap;
+ typedef std::map<LevelLayerRangeKey, Image11 *> ImageMap;
ImageMap mAssociatedImages;
};
+class TextureStorage11_2DMultisample : public TextureStorage11
+{
+ public:
+ TextureStorage11_2DMultisample(Renderer11 *renderer,
+ GLenum internalformat,
+ GLsizei width,
+ GLsizei height,
+ int levels,
+ int samples,
+ bool fixedSampleLocations);
+ ~TextureStorage11_2DMultisample() override;
+
+ gl::Error onDestroy(const gl::Context *context) override;
+
+ gl::Error getResource(const gl::Context *context, const TextureHelper11 **outResource) override;
+ gl::Error getRenderTarget(const gl::Context *context,
+ const gl::ImageIndex &index,
+ RenderTargetD3D **outRT) override;
+
+ gl::Error copyToStorage(const gl::Context *context, TextureStorage *destStorage) override;
+
+ void associateImage(Image11 *image, const gl::ImageIndex &index) override;
+ void disassociateImage(const gl::ImageIndex &index, Image11 *expectedImage) override;
+ void verifyAssociatedImageValid(const gl::ImageIndex &index, Image11 *expectedImage) override;
+ gl::Error releaseAssociatedImage(const gl::Context *context,
+ const gl::ImageIndex &index,
+ Image11 *incomingImage) override;
+
+ protected:
+ gl::Error getSwizzleTexture(const TextureHelper11 **outTexture) override;
+ gl::Error getSwizzleRenderTarget(int mipLevel, const d3d11::RenderTargetView **outRTV) override;
+
+ gl::ErrorOrResult<DropStencil> ensureDropStencilTexture(const gl::Context *context) override;
+
+ gl::Error ensureTextureExists(int mipLevels);
+
+ private:
+ gl::Error createSRV(const gl::Context *context,
+ int baseLevel,
+ int mipLevels,
+ DXGI_FORMAT format,
+ const TextureHelper11 &texture,
+ d3d11::SharedSRV *outSRV) override;
+
+ TextureHelper11 mTexture;
+ std::unique_ptr<RenderTarget11> mRenderTarget;
+
+ unsigned int mSamples;
+ GLboolean mFixedSampleLocations;
+};
}
#endif // LIBANGLE_RENDERER_D3D_D3D11_TEXTURESTORAGE11_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/TransformFeedback11.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/TransformFeedback11.cpp
new file mode 100644
index 0000000000..4b08edf71f
--- /dev/null
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/TransformFeedback11.cpp
@@ -0,0 +1,124 @@
+//
+// Copyright 2014 The ANGLE Project Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+//
+
+// TransformFeedbackD3D.cpp is a no-op implementation for both the D3D9 and D3D11 renderers.
+
+#include "libANGLE/renderer/d3d/d3d11/TransformFeedback11.h"
+
+#include "libANGLE/Buffer.h"
+#include "libANGLE/renderer/d3d/d3d11/Buffer11.h"
+#include "libANGLE/renderer/d3d/d3d11/Renderer11.h"
+
+namespace rx
+{
+
+TransformFeedback11::TransformFeedback11(const gl::TransformFeedbackState &state,
+ Renderer11 *renderer)
+ : TransformFeedbackImpl(state),
+ mRenderer(renderer),
+ mIsDirty(true),
+ mBuffers(state.getIndexedBuffers().size(), nullptr),
+ mBufferOffsets(state.getIndexedBuffers().size(), 0),
+ mSerial(mRenderer->generateSerial())
+{
+}
+
+TransformFeedback11::~TransformFeedback11()
+{
+}
+
+void TransformFeedback11::begin(GLenum primitiveMode)
+{
+ // Reset all the cached offsets to the binding offsets
+ mIsDirty = true;
+ for (size_t bindingIdx = 0; bindingIdx < mBuffers.size(); bindingIdx++)
+ {
+ const auto &binding = mState.getIndexedBuffer(bindingIdx);
+ if (binding.get() != nullptr)
+ {
+ mBufferOffsets[bindingIdx] = static_cast<UINT>(binding.getOffset());
+ }
+ else
+ {
+ mBufferOffsets[bindingIdx] = 0;
+ }
+ }
+}
+
+void TransformFeedback11::end()
+{
+ if (mRenderer->getWorkarounds().flushAfterEndingTransformFeedback)
+ {
+ mRenderer->getDeviceContext()->Flush();
+ }
+}
+
+void TransformFeedback11::pause()
+{
+}
+
+void TransformFeedback11::resume()
+{
+}
+
+void TransformFeedback11::bindGenericBuffer(const gl::BindingPointer<gl::Buffer> &binding)
+{
+}
+
+void TransformFeedback11::bindIndexedBuffer(size_t index,
+ const gl::OffsetBindingPointer<gl::Buffer> &binding)
+{
+ mIsDirty = true;
+ mBufferOffsets[index] = static_cast<UINT>(binding.getOffset());
+}
+
+void TransformFeedback11::onApply()
+{
+ mIsDirty = false;
+
+ // Change all buffer offsets to -1 so that if any of them need to be re-applied, the are set to
+ // append
+ std::fill(mBufferOffsets.begin(), mBufferOffsets.end(), -1);
+}
+
+bool TransformFeedback11::isDirty() const
+{
+ return mIsDirty;
+}
+
+UINT TransformFeedback11::getNumSOBuffers() const
+{
+ return static_cast<UINT>(mBuffers.size());
+}
+
+gl::ErrorOrResult<const std::vector<ID3D11Buffer *> *> TransformFeedback11::getSOBuffers(
+ const gl::Context *context)
+{
+ for (size_t bindingIdx = 0; bindingIdx < mBuffers.size(); bindingIdx++)
+ {
+ const auto &binding = mState.getIndexedBuffer(bindingIdx);
+ if (binding.get() != nullptr)
+ {
+ Buffer11 *storage = GetImplAs<Buffer11>(binding.get());
+ ANGLE_TRY_RESULT(storage->getBuffer(context, BUFFER_USAGE_VERTEX_OR_TRANSFORM_FEEDBACK),
+ mBuffers[bindingIdx]);
+ }
+ }
+
+ return &mBuffers;
+}
+
+const std::vector<UINT> &TransformFeedback11::getSOBufferOffsets() const
+{
+ return mBufferOffsets;
+}
+
+Serial TransformFeedback11::getSerial() const
+{
+ return mSerial;
+}
+
+} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/TransformFeedback11.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/TransformFeedback11.h
new file mode 100644
index 0000000000..cc9fcc335a
--- /dev/null
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/TransformFeedback11.h
@@ -0,0 +1,60 @@
+//
+// Copyright 2014 The ANGLE Project Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+//
+
+// TransformFeedback11.h: Implements the abstract rx::TransformFeedbackImpl class.
+
+#ifndef LIBANGLE_RENDERER_D3D_D3D11_TRANSFORMFEEDBACK11_H_
+#define LIBANGLE_RENDERER_D3D_D3D11_TRANSFORMFEEDBACK11_H_
+
+#include "common/platform.h"
+
+#include "libANGLE/Error.h"
+#include "libANGLE/angletypes.h"
+#include "libANGLE/renderer/TransformFeedbackImpl.h"
+#include "libANGLE/renderer/renderer_utils.h"
+
+namespace rx
+{
+
+class Renderer11;
+
+class TransformFeedback11 : public TransformFeedbackImpl
+{
+ public:
+ TransformFeedback11(const gl::TransformFeedbackState &state, Renderer11 *renderer);
+ ~TransformFeedback11() override;
+
+ void begin(GLenum primitiveMode) override;
+ void end() override;
+ void pause() override;
+ void resume() override;
+
+ void bindGenericBuffer(const gl::BindingPointer<gl::Buffer> &binding) override;
+ void bindIndexedBuffer(size_t index,
+ const gl::OffsetBindingPointer<gl::Buffer> &binding) override;
+
+ void onApply();
+
+ bool isDirty() const;
+
+ UINT getNumSOBuffers() const;
+ gl::ErrorOrResult<const std::vector<ID3D11Buffer *> *> getSOBuffers(const gl::Context *context);
+ const std::vector<UINT> &getSOBufferOffsets() const;
+
+ Serial getSerial() const;
+
+ private:
+ Renderer11 *mRenderer;
+
+ bool mIsDirty;
+ std::vector<ID3D11Buffer *> mBuffers;
+ std::vector<UINT> mBufferOffsets;
+
+ Serial mSerial;
+};
+} // namespace rx
+
+#endif // LIBANGLE_RENDERER_D3D_D3D11_TRANSFORMFEEDBACK11_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Trim11.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Trim11.cpp
index 213ce31817..29185a9d93 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Trim11.cpp
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Trim11.cpp
@@ -11,9 +11,15 @@
#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
#if defined (ANGLE_ENABLE_WINDOWS_STORE)
-using namespace ABI::Windows::Foundation;
+#include <wrl.h>
+#include <wrl/wrappers/corewrappers.h>
+#include <windows.applicationmodel.core.h>
+using namespace Microsoft::WRL;
+using namespace Microsoft::WRL::Wrappers;
using namespace ABI::Windows::ApplicationModel;
using namespace ABI::Windows::ApplicationModel::Core;
+using namespace ABI::Windows::Foundation;
+using namespace ABI::Windows::Foundation::Collections;
#endif
namespace rx
@@ -41,7 +47,6 @@ void Trim11::trim()
#if defined (ANGLE_ENABLE_WINDOWS_STORE)
ID3D11Device* device = mRenderer->getDevice();
- // IDXGIDevice3 is only supported on Windows 8.1 and Windows Phone 8.1 and above.
IDXGIDevice3 *dxgiDevice3 = d3d11::DynamicCastComObject<IDXGIDevice3>(device);
if (dxgiDevice3)
{
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Trim11.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Trim11.h
index 4741e81601..69fa05a57b 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Trim11.h
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/Trim11.h
@@ -13,9 +13,7 @@
#include "libANGLE/angletypes.h"
#include "libANGLE/Error.h"
-#if !defined(ANGLE_ENABLE_WINDOWS_STORE)
-typedef void* EventRegistrationToken;
-#else
+#if defined(ANGLE_ENABLE_WINDOWS_STORE)
#include <EventToken.h>
#endif
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/VertexArray11.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/VertexArray11.cpp
new file mode 100644
index 0000000000..97c29415ed
--- /dev/null
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/VertexArray11.cpp
@@ -0,0 +1,413 @@
+//
+// Copyright 2016 The ANGLE Project Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+//
+// VertexArray11:
+// Implementation of rx::VertexArray11.
+//
+
+#include "libANGLE/renderer/d3d/d3d11/VertexArray11.h"
+
+#include "common/bitset_utils.h"
+#include "libANGLE/Context.h"
+#include "libANGLE/renderer/d3d/d3d11/Buffer11.h"
+#include "libANGLE/renderer/d3d/d3d11/Context11.h"
+
+using namespace angle;
+
+namespace rx
+{
+
+namespace
+{
+OnBufferDataDirtyChannel *GetBufferBroadcastChannel(Buffer11 *buffer11,
+ IndexStorageType storageType)
+{
+ switch (storageType)
+ {
+ case IndexStorageType::Direct:
+ return buffer11->getDirectBroadcastChannel();
+ case IndexStorageType::Static:
+ return buffer11->getStaticBroadcastChannel();
+ case IndexStorageType::Dynamic:
+ return buffer11 ? buffer11->getStaticBroadcastChannel() : nullptr;
+ default:
+ UNREACHABLE();
+ return nullptr;
+ }
+}
+} // anonymous namespace
+
+VertexArray11::VertexArray11(const gl::VertexArrayState &data)
+ : VertexArrayImpl(data),
+ mAttributeStorageTypes(data.getMaxAttribs(), VertexStorageType::CURRENT_VALUE),
+ mTranslatedAttribs(data.getMaxAttribs()),
+ mCurrentArrayBuffers(data.getMaxAttribs()),
+ mCurrentElementArrayBuffer(),
+ mOnArrayBufferDataDirty(),
+ mOnElementArrayBufferDataDirty(this, mCurrentArrayBuffers.size()),
+ mAppliedNumViewsToDivisor(1),
+ mLastElementType(GL_NONE),
+ mLastDrawElementsOffset(0),
+ mCurrentElementArrayStorage(IndexStorageType::Invalid),
+ mCachedIndexInfoValid(false)
+{
+ for (size_t attribIndex = 0; attribIndex < mCurrentArrayBuffers.size(); ++attribIndex)
+ {
+ mOnArrayBufferDataDirty.emplace_back(this, attribIndex);
+ }
+}
+
+VertexArray11::~VertexArray11()
+{
+}
+
+void VertexArray11::destroy(const gl::Context *context)
+{
+ for (auto &buffer : mCurrentArrayBuffers)
+ {
+ if (buffer.get())
+ {
+ buffer.set(context, nullptr);
+ }
+ }
+
+ mCurrentElementArrayBuffer.set(context, nullptr);
+}
+
+void VertexArray11::syncState(const gl::Context *context,
+ const gl::VertexArray::DirtyBits &dirtyBits)
+{
+ ASSERT(dirtyBits.any());
+
+ // Generate a state serial. This serial is used in the program class to validate the cached
+ // input layout, and skip recomputation in the fast path.
+ Renderer11 *renderer = GetImplAs<Context11>(context)->getRenderer();
+ mCurrentStateSerial = renderer->generateSerial();
+
+ // TODO(jmadill): Individual attribute invalidation.
+ renderer->getStateManager()->invalidateVertexBuffer();
+
+ for (auto dirtyBit : dirtyBits)
+ {
+ if (dirtyBit == gl::VertexArray::DIRTY_BIT_ELEMENT_ARRAY_BUFFER)
+ {
+ mCachedIndexInfoValid = false;
+ mLastElementType = GL_NONE;
+ }
+ else
+ {
+ size_t index = gl::VertexArray::GetVertexIndexFromDirtyBit(dirtyBit);
+ // TODO(jiawei.shao@intel.com): Vertex Attrib Bindings
+ ASSERT(index == mState.getBindingIndexFromAttribIndex(index));
+ mAttribsToUpdate.set(index);
+ }
+ }
+}
+
+bool VertexArray11::flushAttribUpdates(const gl::Context *context)
+{
+ if (mAttribsToUpdate.any())
+ {
+ const auto &activeLocations =
+ context->getGLState().getProgram()->getActiveAttribLocationsMask();
+
+ // Skip attrib locations the program doesn't use.
+ gl::AttributesMask activeToUpdate = mAttribsToUpdate & activeLocations;
+
+ for (auto toUpdateIndex : activeToUpdate)
+ {
+ mAttribsToUpdate.reset(toUpdateIndex);
+ updateVertexAttribStorage(context, toUpdateIndex);
+ }
+
+ return true;
+ }
+
+ return false;
+}
+
+bool VertexArray11::updateElementArrayStorage(const gl::Context *context,
+ GLenum elementType,
+ GLenum destElementType,
+ const void *indices)
+{
+ unsigned int offset = static_cast<unsigned int>(reinterpret_cast<uintptr_t>(indices));
+
+ if (mCachedIndexInfoValid && mLastElementType == elementType &&
+ offset == mLastDrawElementsOffset)
+ {
+ // Dynamic index buffers must be re-streamed every draw.
+ return (mCurrentElementArrayStorage == IndexStorageType::Dynamic);
+ }
+
+ gl::Buffer *newBuffer = mState.getElementArrayBuffer().get();
+ gl::Buffer *oldBuffer = mCurrentElementArrayBuffer.get();
+ bool needsTranslation = false;
+ IndexStorageType newStorageType = ClassifyIndexStorage(
+ context->getGLState(), newBuffer, elementType, destElementType, offset, &needsTranslation);
+
+ if (newBuffer != oldBuffer)
+ {
+ mCurrentElementArrayBuffer.set(context, newBuffer);
+ }
+
+ if (newStorageType != mCurrentElementArrayStorage || newBuffer != oldBuffer)
+ {
+ Buffer11 *newBuffer11 = SafeGetImplAs<Buffer11>(newBuffer);
+
+ auto *newChannel = GetBufferBroadcastChannel(newBuffer11, newStorageType);
+
+ mCurrentElementArrayStorage = newStorageType;
+ mOnElementArrayBufferDataDirty.bind(newChannel);
+ needsTranslation = true;
+ }
+
+ if (mLastDrawElementsOffset != offset)
+ {
+ needsTranslation = true;
+ mLastDrawElementsOffset = offset;
+ }
+
+ if (mLastElementType != elementType)
+ {
+ needsTranslation = true;
+ mLastElementType = elementType;
+ }
+
+ // TODO(jmadill): We should probably promote static usage immediately, because this can change
+ // the storage type for dynamic buffers.
+ return needsTranslation || !mCachedIndexInfoValid;
+}
+
+void VertexArray11::updateVertexAttribStorage(const gl::Context *context, size_t attribIndex)
+{
+ const auto &attrib = mState.getVertexAttribute(attribIndex);
+ const auto &binding = mState.getBindingFromAttribIndex(attribIndex);
+
+ // Note: having an unchanged storage type doesn't mean the attribute is clean.
+ auto oldStorageType = mAttributeStorageTypes[attribIndex];
+ auto newStorageType = ClassifyAttributeStorage(attrib, binding);
+
+ mAttributeStorageTypes[attribIndex] = newStorageType;
+
+ StateManager11 *stateManager = GetImplAs<Context11>(context)->getRenderer()->getStateManager();
+
+ if (newStorageType == VertexStorageType::DYNAMIC)
+ {
+ if (oldStorageType != VertexStorageType::DYNAMIC)
+ {
+ // Sync dynamic attribs in a different set.
+ mAttribsToTranslate.reset(attribIndex);
+ mDynamicAttribsMask.set(attribIndex);
+ }
+ }
+ else
+ {
+ mAttribsToTranslate.set(attribIndex);
+ stateManager->invalidateVertexAttributeTranslation();
+
+ if (oldStorageType == VertexStorageType::DYNAMIC)
+ {
+ ASSERT(mDynamicAttribsMask[attribIndex]);
+ mDynamicAttribsMask.reset(attribIndex);
+ }
+ }
+
+ gl::Buffer *oldBufferGL = mCurrentArrayBuffers[attribIndex].get();
+ gl::Buffer *newBufferGL = binding.getBuffer().get();
+ Buffer11 *oldBuffer11 = oldBufferGL ? GetImplAs<Buffer11>(oldBufferGL) : nullptr;
+ Buffer11 *newBuffer11 = newBufferGL ? GetImplAs<Buffer11>(newBufferGL) : nullptr;
+
+ if (oldBuffer11 != newBuffer11 || oldStorageType != newStorageType)
+ {
+ OnBufferDataDirtyChannel *newChannel = nullptr;
+
+ if (newStorageType == VertexStorageType::CURRENT_VALUE)
+ {
+ stateManager->invalidateCurrentValueAttrib(attribIndex);
+ }
+ else if (newBuffer11 != nullptr)
+ {
+ // Note that for static callbacks, promotion to a static buffer from a dynamic buffer
+ // means we need to tag dynamic buffers with static callbacks.
+ switch (newStorageType)
+ {
+ case VertexStorageType::DIRECT:
+ newChannel = newBuffer11->getDirectBroadcastChannel();
+ break;
+ case VertexStorageType::STATIC:
+ case VertexStorageType::DYNAMIC:
+ newChannel = newBuffer11->getStaticBroadcastChannel();
+ break;
+ default:
+ UNREACHABLE();
+ break;
+ }
+ }
+
+ mOnArrayBufferDataDirty[attribIndex].bind(newChannel);
+ mCurrentArrayBuffers[attribIndex].set(context, binding.getBuffer().get());
+ }
+}
+
+bool VertexArray11::hasActiveDynamicAttrib(const gl::Context *context)
+{
+ flushAttribUpdates(context);
+ const auto &activeLocations =
+ context->getGLState().getProgram()->getActiveAttribLocationsMask();
+ auto activeDynamicAttribs = (mDynamicAttribsMask & activeLocations);
+ return activeDynamicAttribs.any();
+}
+
+gl::Error VertexArray11::updateDirtyAndDynamicAttribs(const gl::Context *context,
+ VertexDataManager *vertexDataManager,
+ const DrawCallVertexParams &vertexParams)
+{
+ flushAttribUpdates(context);
+
+ const auto &glState = context->getGLState();
+ const gl::Program *program = glState.getProgram();
+ const auto &activeLocations = program->getActiveAttribLocationsMask();
+ const auto &attribs = mState.getVertexAttributes();
+ const auto &bindings = mState.getVertexBindings();
+ mAppliedNumViewsToDivisor =
+ (program != nullptr && program->usesMultiview()) ? program->getNumViews() : 1;
+
+ if (mAttribsToTranslate.any())
+ {
+ // Skip attrib locations the program doesn't use, saving for the next frame.
+ gl::AttributesMask dirtyActiveAttribs = (mAttribsToTranslate & activeLocations);
+
+ for (auto dirtyAttribIndex : dirtyActiveAttribs)
+ {
+ mAttribsToTranslate.reset(dirtyAttribIndex);
+
+ auto *translatedAttrib = &mTranslatedAttribs[dirtyAttribIndex];
+ const auto &currentValue = glState.getVertexAttribCurrentValue(dirtyAttribIndex);
+
+ // Record basic attrib info
+ translatedAttrib->attribute = &attribs[dirtyAttribIndex];
+ translatedAttrib->binding = &bindings[translatedAttrib->attribute->bindingIndex];
+ translatedAttrib->currentValueType = currentValue.Type;
+ translatedAttrib->divisor =
+ translatedAttrib->binding->getDivisor() * mAppliedNumViewsToDivisor;
+
+ switch (mAttributeStorageTypes[dirtyAttribIndex])
+ {
+ case VertexStorageType::DIRECT:
+ VertexDataManager::StoreDirectAttrib(translatedAttrib);
+ break;
+ case VertexStorageType::STATIC:
+ {
+ ANGLE_TRY(VertexDataManager::StoreStaticAttrib(context, translatedAttrib));
+ break;
+ }
+ case VertexStorageType::CURRENT_VALUE:
+ // Current value attribs are managed by the StateManager11.
+ break;
+ default:
+ UNREACHABLE();
+ break;
+ }
+ }
+ }
+
+ if (mDynamicAttribsMask.any())
+ {
+ auto activeDynamicAttribs = (mDynamicAttribsMask & activeLocations);
+ if (activeDynamicAttribs.none())
+ {
+ return gl::NoError();
+ }
+
+ for (auto dynamicAttribIndex : activeDynamicAttribs)
+ {
+ auto *dynamicAttrib = &mTranslatedAttribs[dynamicAttribIndex];
+ const auto &currentValue = glState.getVertexAttribCurrentValue(dynamicAttribIndex);
+
+ // Record basic attrib info
+ dynamicAttrib->attribute = &attribs[dynamicAttribIndex];
+ dynamicAttrib->binding = &bindings[dynamicAttrib->attribute->bindingIndex];
+ dynamicAttrib->currentValueType = currentValue.Type;
+ dynamicAttrib->divisor =
+ dynamicAttrib->binding->getDivisor() * mAppliedNumViewsToDivisor;
+ }
+
+ ANGLE_TRY(vertexDataManager->storeDynamicAttribs(
+ context, &mTranslatedAttribs, activeDynamicAttribs, vertexParams.firstVertex(),
+ vertexParams.vertexCount(), vertexParams.instances()));
+ }
+
+ return gl::NoError();
+}
+
+const std::vector<TranslatedAttribute> &VertexArray11::getTranslatedAttribs() const
+{
+ return mTranslatedAttribs;
+}
+
+void VertexArray11::signal(size_t channelID, const gl::Context *context)
+{
+ if (channelID == mAttributeStorageTypes.size())
+ {
+ mCachedIndexInfoValid = false;
+ mLastElementType = GL_NONE;
+ mLastDrawElementsOffset = 0;
+ }
+ else
+ {
+ ASSERT(mAttributeStorageTypes[channelID] != VertexStorageType::CURRENT_VALUE);
+
+ // This can change a buffer's storage, we'll need to re-check.
+ mAttribsToUpdate.set(channelID);
+
+ // Changing the vertex attribute state can affect the vertex shader.
+ Renderer11 *renderer = GetImplAs<Context11>(context)->getRenderer();
+ renderer->getStateManager()->invalidateShaders();
+ }
+}
+
+void VertexArray11::clearDirtyAndPromoteDynamicAttribs(const gl::Context *context,
+ const DrawCallVertexParams &vertexParams)
+{
+ const gl::State &state = context->getGLState();
+ const gl::Program *program = state.getProgram();
+ const auto &activeLocations = program->getActiveAttribLocationsMask();
+ mAttribsToUpdate &= ~activeLocations;
+
+ // Promote to static after we clear the dirty attributes, otherwise we can lose dirtyness.
+ auto activeDynamicAttribs = (mDynamicAttribsMask & activeLocations);
+ if (activeDynamicAttribs.any())
+ {
+ VertexDataManager::PromoteDynamicAttribs(context, mTranslatedAttribs, activeDynamicAttribs,
+ vertexParams.vertexCount());
+ }
+}
+
+void VertexArray11::markAllAttributeDivisorsForAdjustment(int numViews)
+{
+ if (mAppliedNumViewsToDivisor != numViews)
+ {
+ mAppliedNumViewsToDivisor = numViews;
+ mAttribsToUpdate.set();
+ }
+}
+
+TranslatedIndexData *VertexArray11::getCachedIndexInfo()
+{
+ return &mCachedIndexInfo;
+}
+
+void VertexArray11::setCachedIndexInfoValid()
+{
+ mCachedIndexInfoValid = true;
+}
+
+bool VertexArray11::isCachedIndexInfoValid() const
+{
+ return mCachedIndexInfoValid;
+}
+
+} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/VertexArray11.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/VertexArray11.h
index b397140e71..4cdc92531d 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/VertexArray11.h
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/VertexArray11.h
@@ -9,23 +9,91 @@
#ifndef LIBANGLE_RENDERER_D3D_D3D11_VERTEXARRAY11_H_
#define LIBANGLE_RENDERER_D3D_D3D11_VERTEXARRAY11_H_
+#include "libANGLE/Framebuffer.h"
#include "libANGLE/renderer/VertexArrayImpl.h"
#include "libANGLE/renderer/d3d/d3d11/Renderer11.h"
+#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
+#include "libANGLE/signal_utils.h"
namespace rx
{
class Renderer11;
-class VertexArray11 : public VertexArrayImpl
+class VertexArray11 : public VertexArrayImpl, public OnBufferDataDirtyReceiver
{
public:
- VertexArray11(const gl::VertexArray::Data &data)
- : VertexArrayImpl(data)
- {
- }
- virtual ~VertexArray11() {}
+ VertexArray11(const gl::VertexArrayState &data);
+ ~VertexArray11() override;
+ void destroy(const gl::Context *context) override;
+
+ void syncState(const gl::Context *context,
+ const gl::VertexArray::DirtyBits &dirtyBits) override;
+ // This will flush any pending attrib updates and then check the dynamic attribs mask.
+ bool hasActiveDynamicAttrib(const gl::Context *context);
+ gl::Error updateDirtyAndDynamicAttribs(const gl::Context *context,
+ VertexDataManager *vertexDataManager,
+ const DrawCallVertexParams &vertexParams);
+ void clearDirtyAndPromoteDynamicAttribs(const gl::Context *context,
+ const DrawCallVertexParams &vertexParams);
+
+ const std::vector<TranslatedAttribute> &getTranslatedAttribs() const;
+
+ // SignalReceiver implementation
+ void signal(size_t channelID, const gl::Context *context) override;
+
+ Serial getCurrentStateSerial() const { return mCurrentStateSerial; }
+
+ // In case of a multi-view program change, we have to update all attributes so that the divisor
+ // is adjusted.
+ void markAllAttributeDivisorsForAdjustment(int numViews);
+
+ bool flushAttribUpdates(const gl::Context *context);
+
+ // Returns true if the element array buffer needs to be translated.
+ bool updateElementArrayStorage(const gl::Context *context,
+ GLenum elementType,
+ GLenum destElementType,
+ const void *indices);
+
+ TranslatedIndexData *getCachedIndexInfo();
+ void setCachedIndexInfoValid();
+ bool isCachedIndexInfoValid() const;
+
+ private:
+ void updateVertexAttribStorage(const gl::Context *context, size_t attribIndex);
+
+ std::vector<VertexStorageType> mAttributeStorageTypes;
+ std::vector<TranslatedAttribute> mTranslatedAttribs;
+
+ // The mask of attributes marked as dynamic.
+ gl::AttributesMask mDynamicAttribsMask;
+
+ // A mask of attributes that need to be re-evaluated.
+ gl::AttributesMask mAttribsToUpdate;
+
+ // A set of attributes we know are dirty, and need to be re-translated.
+ gl::AttributesMask mAttribsToTranslate;
+
+ // We need to keep a safe pointer to the Buffer so we can attach the correct dirty callbacks.
+ std::vector<gl::BindingPointer<gl::Buffer>> mCurrentArrayBuffers;
+ gl::BindingPointer<gl::Buffer> mCurrentElementArrayBuffer;
+
+ std::vector<OnBufferDataDirtyBinding> mOnArrayBufferDataDirty;
+ OnBufferDataDirtyBinding mOnElementArrayBufferDataDirty;
+
+ Serial mCurrentStateSerial;
+
+ // The numViews value used to adjust the divisor.
+ int mAppliedNumViewsToDivisor;
+
+ // If the index buffer needs re-streaming.
+ GLenum mLastElementType;
+ unsigned int mLastDrawElementsOffset;
+ IndexStorageType mCurrentElementArrayStorage;
+ TranslatedIndexData mCachedIndexInfo;
+ bool mCachedIndexInfoValid;
};
-}
+} // namespace rx
#endif // LIBANGLE_RENDERER_D3D_D3D11_VERTEXARRAY11_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/VertexBuffer11.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/VertexBuffer11.cpp
index 098cefcd53..611bd0f18b 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/VertexBuffer11.cpp
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/VertexBuffer11.cpp
@@ -19,92 +19,88 @@
namespace rx
{
-VertexBuffer11::VertexBuffer11(Renderer11 *const renderer) : mRenderer(renderer)
+VertexBuffer11::VertexBuffer11(Renderer11 *const renderer)
+ : mRenderer(renderer),
+ mBuffer(),
+ mBufferSize(0),
+ mDynamicUsage(false),
+ mMappedResourceData(nullptr)
{
- mBuffer = NULL;
- mBufferSize = 0;
- mDynamicUsage = false;
- mMappedResourceData = NULL;
}
VertexBuffer11::~VertexBuffer11()
{
- ASSERT(mMappedResourceData == NULL);
- SafeRelease(mBuffer);
+ ASSERT(mMappedResourceData == nullptr);
}
gl::Error VertexBuffer11::initialize(unsigned int size, bool dynamicUsage)
{
- SafeRelease(mBuffer);
-
+ mBuffer.reset();
updateSerial();
if (size > 0)
{
- ID3D11Device* dxDevice = mRenderer->getDevice();
-
D3D11_BUFFER_DESC bufferDesc;
- bufferDesc.ByteWidth = size;
- bufferDesc.Usage = D3D11_USAGE_DYNAMIC;
- bufferDesc.BindFlags = D3D11_BIND_VERTEX_BUFFER;
- bufferDesc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE;
- bufferDesc.MiscFlags = 0;
+ bufferDesc.ByteWidth = size;
+ bufferDesc.Usage = D3D11_USAGE_DYNAMIC;
+ bufferDesc.BindFlags = D3D11_BIND_VERTEX_BUFFER;
+ bufferDesc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE;
+ bufferDesc.MiscFlags = 0;
bufferDesc.StructureByteStride = 0;
- HRESULT result = dxDevice->CreateBuffer(&bufferDesc, NULL, &mBuffer);
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to allocate internal vertex buffer of size, %lu.", size);
- }
+ ANGLE_TRY(mRenderer->allocateResource(bufferDesc, &mBuffer));
if (dynamicUsage)
{
- d3d11::SetDebugName(mBuffer, "VertexBuffer11 (dynamic)");
+ mBuffer.setDebugName("VertexBuffer11 (dynamic)");
}
else
{
- d3d11::SetDebugName(mBuffer, "VertexBuffer11 (static)");
+ mBuffer.setDebugName("VertexBuffer11 (static)");
}
}
- mBufferSize = size;
+ mBufferSize = size;
mDynamicUsage = dynamicUsage;
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
gl::Error VertexBuffer11::mapResource()
{
- if (mMappedResourceData == NULL)
+ if (mMappedResourceData == nullptr)
{
ID3D11DeviceContext *dxContext = mRenderer->getDeviceContext();
D3D11_MAPPED_SUBRESOURCE mappedResource;
- HRESULT result = dxContext->Map(mBuffer, 0, D3D11_MAP_WRITE_NO_OVERWRITE, 0, &mappedResource);
+ HRESULT result =
+ dxContext->Map(mBuffer.get(), 0, D3D11_MAP_WRITE_NO_OVERWRITE, 0, &mappedResource);
if (FAILED(result))
{
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to map internal vertex buffer, HRESULT: 0x%08x.", result);
+ return gl::OutOfMemory()
+ << "Failed to map internal vertex buffer, " << gl::FmtHR(result);
}
- mMappedResourceData = reinterpret_cast<uint8_t*>(mappedResource.pData);
+ mMappedResourceData = reinterpret_cast<uint8_t *>(mappedResource.pData);
}
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
void VertexBuffer11::hintUnmapResource()
{
- if (mMappedResourceData != NULL)
+ if (mMappedResourceData != nullptr)
{
ID3D11DeviceContext *dxContext = mRenderer->getDeviceContext();
- dxContext->Unmap(mBuffer, 0);
+ dxContext->Unmap(mBuffer.get(), 0);
- mMappedResourceData = NULL;
+ mMappedResourceData = nullptr;
}
}
gl::Error VertexBuffer11::storeVertexAttributes(const gl::VertexAttribute &attrib,
+ const gl::VertexBinding &binding,
GLenum currentValueType,
GLint start,
GLsizei count,
@@ -112,81 +108,33 @@ gl::Error VertexBuffer11::storeVertexAttributes(const gl::VertexAttribute &attri
unsigned int offset,
const uint8_t *sourceData)
{
- if (!mBuffer)
+ if (!mBuffer.valid())
{
- return gl::Error(GL_OUT_OF_MEMORY, "Internal vertex buffer is not initialized.");
+ return gl::OutOfMemory() << "Internal vertex buffer is not initialized.";
}
- int inputStride = static_cast<int>(ComputeVertexAttributeStride(attrib));
+ int inputStride = static_cast<int>(ComputeVertexAttributeStride(attrib, binding));
// This will map the resource if it isn't already mapped.
- gl::Error error = mapResource();
- if (error.isError())
- {
- return error;
- }
+ ANGLE_TRY(mapResource());
uint8_t *output = mMappedResourceData + offset;
const uint8_t *input = sourceData;
- if (instances == 0 || attrib.divisor == 0)
+ if (instances == 0 || binding.getDivisor() == 0)
{
input += inputStride * start;
}
gl::VertexFormatType vertexFormatType = gl::GetVertexFormatType(attrib, currentValueType);
- const D3D_FEATURE_LEVEL featureLevel = mRenderer->getRenderer11DeviceCaps().featureLevel;
- const d3d11::VertexFormat &vertexFormatInfo = d3d11::GetVertexFormatInfo(vertexFormatType, featureLevel);
- ASSERT(vertexFormatInfo.copyFunction != NULL);
+ const D3D_FEATURE_LEVEL featureLevel = mRenderer->getRenderer11DeviceCaps().featureLevel;
+ const d3d11::VertexFormat &vertexFormatInfo =
+ d3d11::GetVertexFormatInfo(vertexFormatType, featureLevel);
+ ASSERT(vertexFormatInfo.copyFunction != nullptr);
vertexFormatInfo.copyFunction(input, inputStride, count, output);
- return gl::Error(GL_NO_ERROR);
-}
-
-gl::Error VertexBuffer11::getSpaceRequired(const gl::VertexAttribute &attrib, GLsizei count,
- GLsizei instances, unsigned int *outSpaceRequired) const
-{
- unsigned int elementCount = 0;
- if (attrib.enabled)
- {
- if (instances == 0 || attrib.divisor == 0)
- {
- elementCount = count;
- }
- else
- {
- // Round up to divisor, if possible
- elementCount = UnsignedCeilDivide(static_cast<unsigned int>(instances), attrib.divisor);
- }
-
- gl::VertexFormatType formatType = gl::GetVertexFormatType(attrib);
- const D3D_FEATURE_LEVEL featureLevel = mRenderer->getRenderer11DeviceCaps().featureLevel;
- const d3d11::VertexFormat &vertexFormatInfo = d3d11::GetVertexFormatInfo(formatType, featureLevel);
- const d3d11::DXGIFormat &dxgiFormatInfo = d3d11::GetDXGIFormatInfo(vertexFormatInfo.nativeFormat);
- unsigned int elementSize = dxgiFormatInfo.pixelBytes;
- if (elementSize <= std::numeric_limits<unsigned int>::max() / elementCount)
- {
- if (outSpaceRequired)
- {
- *outSpaceRequired = elementSize * elementCount;
- }
- return gl::Error(GL_NO_ERROR);
- }
- else
- {
- return gl::Error(GL_OUT_OF_MEMORY, "New vertex buffer size would result in an overflow.");
- }
- }
- else
- {
- const unsigned int elementSize = 4;
- if (outSpaceRequired)
- {
- *outSpaceRequired = elementSize * 4;
- }
- return gl::Error(GL_NO_ERROR);
- }
+ return gl::NoError();
}
unsigned int VertexBuffer11::getBufferSize() const
@@ -202,34 +150,35 @@ gl::Error VertexBuffer11::setBufferSize(unsigned int size)
}
else
{
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
}
gl::Error VertexBuffer11::discard()
{
- if (!mBuffer)
+ if (!mBuffer.valid())
{
- return gl::Error(GL_OUT_OF_MEMORY, "Internal vertex buffer is not initialized.");
+ return gl::OutOfMemory() << "Internal vertex buffer is not initialized.";
}
ID3D11DeviceContext *dxContext = mRenderer->getDeviceContext();
D3D11_MAPPED_SUBRESOURCE mappedResource;
- HRESULT result = dxContext->Map(mBuffer, 0, D3D11_MAP_WRITE_DISCARD, 0, &mappedResource);
+ HRESULT result = dxContext->Map(mBuffer.get(), 0, D3D11_MAP_WRITE_DISCARD, 0, &mappedResource);
if (FAILED(result))
{
- return gl::Error(GL_OUT_OF_MEMORY, "Failed to map internal buffer for discarding, HRESULT: 0x%08x", result);
+ return gl::OutOfMemory() << "Failed to map internal buffer for discarding, "
+ << gl::FmtHR(result);
}
- dxContext->Unmap(mBuffer, 0);
+ dxContext->Unmap(mBuffer.get(), 0);
- return gl::Error(GL_NO_ERROR);
+ return gl::NoError();
}
-ID3D11Buffer *VertexBuffer11::getBuffer() const
+const d3d11::Buffer &VertexBuffer11::getBuffer() const
{
return mBuffer;
}
-}
+} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/VertexBuffer11.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/VertexBuffer11.h
index 773c4474e1..ab619ae503 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/VertexBuffer11.h
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/VertexBuffer11.h
@@ -12,6 +12,7 @@
#include <stdint.h>
#include "libANGLE/renderer/d3d/VertexBuffer.h"
+#include "libANGLE/renderer/d3d/d3d11/ResourceManager11.h"
namespace rx
{
@@ -21,11 +22,13 @@ class VertexBuffer11 : public VertexBuffer
{
public:
explicit VertexBuffer11(Renderer11 *const renderer);
- virtual ~VertexBuffer11();
- virtual gl::Error initialize(unsigned int size, bool dynamicUsage);
+ gl::Error initialize(unsigned int size, bool dynamicUsage) override;
+ // Warning: you should ensure binding really matches attrib.bindingIndex before using this
+ // function.
gl::Error storeVertexAttributes(const gl::VertexAttribute &attrib,
+ const gl::VertexBinding &binding,
GLenum currentValueType,
GLint start,
GLsizei count,
@@ -33,29 +36,27 @@ class VertexBuffer11 : public VertexBuffer
unsigned int offset,
const uint8_t *sourceData) override;
- virtual gl::Error getSpaceRequired(const gl::VertexAttribute &attrib, GLsizei count, GLsizei instances,
- unsigned int *outSpaceRequired) const;
+ unsigned int getBufferSize() const override;
+ gl::Error setBufferSize(unsigned int size) override;
+ gl::Error discard() override;
- virtual unsigned int getBufferSize() const;
- virtual gl::Error setBufferSize(unsigned int size);
- virtual gl::Error discard();
+ void hintUnmapResource() override;
- virtual void hintUnmapResource();
-
- ID3D11Buffer *getBuffer() const;
+ const d3d11::Buffer &getBuffer() const;
private:
+ ~VertexBuffer11() override;
gl::Error mapResource();
Renderer11 *const mRenderer;
- ID3D11Buffer *mBuffer;
+ d3d11::Buffer mBuffer;
unsigned int mBufferSize;
bool mDynamicUsage;
uint8_t *mMappedResourceData;
};
-}
+} // namespace rx
#endif // LIBANGLE_RENDERER_D3D_D3D11_VERTEXBUFFER11_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/copyvertex.inl b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/copyvertex.inl
index 1ec21dee55..7c5c157c6f 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/copyvertex.inl
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/copyvertex.inl
@@ -15,33 +15,42 @@ inline void CopyNativeVertexData(const uint8_t *input, size_t stride, size_t cou
if (attribSize == stride && inputComponentCount == outputComponentCount)
{
memcpy(output, input, count * attribSize);
+ return;
}
- else
- {
- const T defaultAlphaValue = gl::bitCast<T>(alphaDefaultValueBits);
- const size_t lastNonAlphaOutputComponent = std::min<size_t>(outputComponentCount, 3);
+ if (inputComponentCount == outputComponentCount)
+ {
for (size_t i = 0; i < count; i++)
{
const T *offsetInput = reinterpret_cast<const T*>(input + (i * stride));
T *offsetOutput = reinterpret_cast<T*>(output) + i * outputComponentCount;
- for (size_t j = 0; j < inputComponentCount; j++)
- {
- offsetOutput[j] = offsetInput[j];
- }
+ memcpy(offsetOutput, offsetInput, attribSize);
+ }
+ return;
+ }
- for (size_t j = inputComponentCount; j < lastNonAlphaOutputComponent; j++)
- {
- // Set the remaining G/B channels to 0.
- offsetOutput[j] = 0;
- }
+ const T defaultAlphaValue = gl::bitCast<T>(alphaDefaultValueBits);
+ const size_t lastNonAlphaOutputComponent = std::min<size_t>(outputComponentCount, 3);
- if (inputComponentCount < outputComponentCount && outputComponentCount == 4)
- {
- // Set the remaining alpha channel to the defaultAlphaValue.
- offsetOutput[3] = defaultAlphaValue;
- }
+ for (size_t i = 0; i < count; i++)
+ {
+ const T *offsetInput = reinterpret_cast<const T*>(input + (i * stride));
+ T *offsetOutput = reinterpret_cast<T*>(output) + i * outputComponentCount;
+
+ memcpy(offsetOutput, offsetInput, attribSize);
+
+ if (inputComponentCount < lastNonAlphaOutputComponent)
+ {
+ // Set the remaining G/B channels to 0.
+ size_t numComponents = (lastNonAlphaOutputComponent - inputComponentCount);
+ memset(&offsetOutput[inputComponentCount], 0, numComponents * sizeof(T));
+ }
+
+ if (inputComponentCount < outputComponentCount && outputComponentCount == 4)
+ {
+ // Set the remaining alpha channel to the defaultAlphaValue.
+ offsetOutput[3] = defaultAlphaValue;
}
}
}
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/dxgi_format_data.json b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/dxgi_format_data.json
new file mode 100644
index 0000000000..891d30d252
--- /dev/null
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/dxgi_format_data.json
@@ -0,0 +1,118 @@
+{
+ "UNKNOWN": "NONE",
+ "R32G32B32A32_TYPELESS": "",
+ "R32G32B32A32_FLOAT": "",
+ "R32G32B32A32_UINT": "",
+ "R32G32B32A32_SINT": "",
+ "R32G32B32_TYPELESS": "",
+ "R32G32B32_FLOAT": "",
+ "R32G32B32_UINT": "",
+ "R32G32B32_SINT": "",
+ "R16G16B16A16_TYPELESS": "",
+ "R16G16B16A16_FLOAT": "",
+ "R16G16B16A16_UNORM": "",
+ "R16G16B16A16_UINT": "",
+ "R16G16B16A16_SNORM": "",
+ "R16G16B16A16_SINT": "",
+ "R32G32_TYPELESS": "",
+ "R32G32_FLOAT": "",
+ "R32G32_UINT": "",
+ "R32G32_SINT": "",
+ "R32G8X24_TYPELESS": "",
+ "D32_FLOAT_S8X24_UINT": "",
+ "R32_FLOAT_X8X24_TYPELESS": "",
+ "X32_TYPELESS_G8X24_UINT": "",
+ "R10G10B10A2_TYPELESS": "",
+ "R10G10B10A2_UNORM": "",
+ "R10G10B10A2_UINT": "",
+ "R11G11B10_FLOAT": "",
+ "R8G8B8A8_TYPELESS": "",
+ "R8G8B8A8_UNORM": "",
+ "R8G8B8A8_UNORM_SRGB": "",
+ "R8G8B8A8_UINT": "",
+ "R8G8B8A8_SNORM": "",
+ "R8G8B8A8_SINT": "",
+ "R16G16_TYPELESS": "",
+ "R16G16_FLOAT": "",
+ "R16G16_UNORM": "",
+ "R16G16_UINT": "",
+ "R16G16_SNORM": "",
+ "R16G16_SINT": "",
+ "R32_TYPELESS": "",
+ "D32_FLOAT": "",
+ "R32_FLOAT": "",
+ "R32_UINT": "",
+ "R32_SINT": "",
+ "R24G8_TYPELESS": "",
+ "D24_UNORM_S8_UINT": "",
+ "R24_UNORM_X8_TYPELESS": "",
+ "X24_TYPELESS_G8_UINT": "",
+ "R8G8_TYPELESS": "",
+ "R8G8_UNORM": "",
+ "R8G8_UINT": "",
+ "R8G8_SNORM": "",
+ "R8G8_SINT": "",
+ "R16_TYPELESS": "",
+ "R16_FLOAT": "",
+ "D16_UNORM": "",
+ "R16_UNORM": "",
+ "R16_UINT": "",
+ "R16_SNORM": "",
+ "R16_SINT": "",
+ "R8_TYPELESS": "",
+ "R8_UNORM": "",
+ "R8_UINT": "",
+ "R8_SNORM": "",
+ "R8_SINT": "",
+ "A8_UNORM": "",
+ "R1_UNORM": "",
+ "R9G9B9E5_SHAREDEXP": "",
+ "R8G8_B8G8_UNORM": "",
+ "G8R8_G8B8_UNORM": "",
+ "BC1_TYPELESS": "",
+ "BC1_UNORM": "BC1_RGBA_UNORM_BLOCK",
+ "BC1_UNORM_SRGB": "BC1_RGBA_UNORM_SRGB_BLOCK",
+ "BC2_TYPELESS": "",
+ "BC2_UNORM": "BC2_RGBA_UNORM_BLOCK",
+ "BC2_UNORM_SRGB": "BC2_RGBA_UNORM_SRGB_BLOCK",
+ "BC3_TYPELESS": "",
+ "BC3_UNORM": "BC3_RGBA_UNORM_BLOCK",
+ "BC3_UNORM_SRGB": "BC3_RGBA_UNORM_SRGB_BLOCK",
+ "BC4_TYPELESS": "",
+ "BC4_UNORM": "",
+ "BC4_SNORM": "",
+ "BC5_TYPELESS": "",
+ "BC5_UNORM": "",
+ "BC5_SNORM": "",
+ "B5G6R5_UNORM": "",
+ "B5G5R5A1_UNORM": "",
+ "B8G8R8A8_UNORM": "",
+ "B8G8R8X8_UNORM": "",
+ "R10G10B10_XR_BIAS_A2_UNORM": "",
+ "B8G8R8A8_TYPELESS": "",
+ "B8G8R8A8_UNORM_SRGB": "",
+ "B8G8R8X8_TYPELESS": "",
+ "B8G8R8X8_UNORM_SRGB": "",
+ "BC6H_TYPELESS": "",
+ "BC6H_UF16": "",
+ "BC6H_SF16": "",
+ "BC7_TYPELESS": "",
+ "BC7_UNORM": "",
+ "BC7_UNORM_SRGB": "",
+ "AYUV": "",
+ "Y410": "",
+ "Y416": "",
+ "NV12": "",
+ "P010": "",
+ "P016": "",
+ "420_OPAQUE": "",
+ "YUY2": "",
+ "Y210": "",
+ "Y216": "",
+ "NV11": "",
+ "AI44": "",
+ "IA44": "",
+ "P8": "",
+ "A8P8": "",
+ "B4G4R4A4_UNORM": ""
+}
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/dxgi_format_map_autogen.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/dxgi_format_map_autogen.cpp
new file mode 100644
index 0000000000..b0697bc5db
--- /dev/null
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/dxgi_format_map_autogen.cpp
@@ -0,0 +1,516 @@
+// GENERATED FILE - DO NOT EDIT.
+// Generated by gen_dxgi_format_table.py using data from dxgi_format_data.json.
+//
+// Copyright 2017 The ANGLE Project Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+//
+// DXGI format info:
+// Determining metadata about a DXGI format.
+
+#include "libANGLE/renderer/Format.h"
+
+using namespace angle;
+
+namespace rx
+{
+
+namespace d3d11
+{
+
+GLenum GetComponentType(DXGI_FORMAT dxgiFormat)
+{
+ switch (dxgiFormat)
+ {
+ case DXGI_FORMAT_420_OPAQUE:
+ break;
+ case DXGI_FORMAT_A8P8:
+ break;
+ case DXGI_FORMAT_A8_UNORM:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_AI44:
+ break;
+ case DXGI_FORMAT_AYUV:
+ break;
+ case DXGI_FORMAT_B4G4R4A4_UNORM:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_B5G5R5A1_UNORM:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_B5G6R5_UNORM:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_B8G8R8A8_TYPELESS:
+ break;
+ case DXGI_FORMAT_B8G8R8A8_UNORM:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_B8G8R8X8_TYPELESS:
+ break;
+ case DXGI_FORMAT_B8G8R8X8_UNORM:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_BC1_TYPELESS:
+ break;
+ case DXGI_FORMAT_BC1_UNORM:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_BC1_UNORM_SRGB:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_BC2_TYPELESS:
+ break;
+ case DXGI_FORMAT_BC2_UNORM:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_BC2_UNORM_SRGB:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_BC3_TYPELESS:
+ break;
+ case DXGI_FORMAT_BC3_UNORM:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_BC3_UNORM_SRGB:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_BC4_SNORM:
+ return GL_SIGNED_NORMALIZED;
+ case DXGI_FORMAT_BC4_TYPELESS:
+ break;
+ case DXGI_FORMAT_BC4_UNORM:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_BC5_SNORM:
+ return GL_SIGNED_NORMALIZED;
+ case DXGI_FORMAT_BC5_TYPELESS:
+ break;
+ case DXGI_FORMAT_BC5_UNORM:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_BC6H_SF16:
+ break;
+ case DXGI_FORMAT_BC6H_TYPELESS:
+ break;
+ case DXGI_FORMAT_BC6H_UF16:
+ break;
+ case DXGI_FORMAT_BC7_TYPELESS:
+ break;
+ case DXGI_FORMAT_BC7_UNORM:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_BC7_UNORM_SRGB:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_D16_UNORM:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_D24_UNORM_S8_UINT:
+ break;
+ case DXGI_FORMAT_D32_FLOAT:
+ return GL_FLOAT;
+ case DXGI_FORMAT_D32_FLOAT_S8X24_UINT:
+ break;
+ case DXGI_FORMAT_G8R8_G8B8_UNORM:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_IA44:
+ break;
+ case DXGI_FORMAT_NV11:
+ break;
+ case DXGI_FORMAT_NV12:
+ break;
+ case DXGI_FORMAT_P010:
+ break;
+ case DXGI_FORMAT_P016:
+ break;
+ case DXGI_FORMAT_P8:
+ break;
+ case DXGI_FORMAT_R10G10B10A2_TYPELESS:
+ break;
+ case DXGI_FORMAT_R10G10B10A2_UINT:
+ return GL_UNSIGNED_INT;
+ case DXGI_FORMAT_R10G10B10A2_UNORM:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_R11G11B10_FLOAT:
+ return GL_FLOAT;
+ case DXGI_FORMAT_R16G16B16A16_FLOAT:
+ return GL_FLOAT;
+ case DXGI_FORMAT_R16G16B16A16_SINT:
+ return GL_INT;
+ case DXGI_FORMAT_R16G16B16A16_SNORM:
+ return GL_SIGNED_NORMALIZED;
+ case DXGI_FORMAT_R16G16B16A16_TYPELESS:
+ break;
+ case DXGI_FORMAT_R16G16B16A16_UINT:
+ return GL_UNSIGNED_INT;
+ case DXGI_FORMAT_R16G16B16A16_UNORM:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_R16G16_FLOAT:
+ return GL_FLOAT;
+ case DXGI_FORMAT_R16G16_SINT:
+ return GL_INT;
+ case DXGI_FORMAT_R16G16_SNORM:
+ return GL_SIGNED_NORMALIZED;
+ case DXGI_FORMAT_R16G16_TYPELESS:
+ break;
+ case DXGI_FORMAT_R16G16_UINT:
+ return GL_UNSIGNED_INT;
+ case DXGI_FORMAT_R16G16_UNORM:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_R16_FLOAT:
+ return GL_FLOAT;
+ case DXGI_FORMAT_R16_SINT:
+ return GL_INT;
+ case DXGI_FORMAT_R16_SNORM:
+ return GL_SIGNED_NORMALIZED;
+ case DXGI_FORMAT_R16_TYPELESS:
+ break;
+ case DXGI_FORMAT_R16_UINT:
+ return GL_UNSIGNED_INT;
+ case DXGI_FORMAT_R16_UNORM:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_R1_UNORM:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_R24G8_TYPELESS:
+ break;
+ case DXGI_FORMAT_R24_UNORM_X8_TYPELESS:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_R32G32B32A32_FLOAT:
+ return GL_FLOAT;
+ case DXGI_FORMAT_R32G32B32A32_SINT:
+ return GL_INT;
+ case DXGI_FORMAT_R32G32B32A32_TYPELESS:
+ break;
+ case DXGI_FORMAT_R32G32B32A32_UINT:
+ return GL_UNSIGNED_INT;
+ case DXGI_FORMAT_R32G32B32_FLOAT:
+ return GL_FLOAT;
+ case DXGI_FORMAT_R32G32B32_SINT:
+ return GL_INT;
+ case DXGI_FORMAT_R32G32B32_TYPELESS:
+ break;
+ case DXGI_FORMAT_R32G32B32_UINT:
+ return GL_UNSIGNED_INT;
+ case DXGI_FORMAT_R32G32_FLOAT:
+ return GL_FLOAT;
+ case DXGI_FORMAT_R32G32_SINT:
+ return GL_INT;
+ case DXGI_FORMAT_R32G32_TYPELESS:
+ break;
+ case DXGI_FORMAT_R32G32_UINT:
+ return GL_UNSIGNED_INT;
+ case DXGI_FORMAT_R32G8X24_TYPELESS:
+ break;
+ case DXGI_FORMAT_R32_FLOAT:
+ return GL_FLOAT;
+ case DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS:
+ return GL_FLOAT;
+ case DXGI_FORMAT_R32_SINT:
+ return GL_INT;
+ case DXGI_FORMAT_R32_TYPELESS:
+ break;
+ case DXGI_FORMAT_R32_UINT:
+ return GL_UNSIGNED_INT;
+ case DXGI_FORMAT_R8G8B8A8_SINT:
+ return GL_INT;
+ case DXGI_FORMAT_R8G8B8A8_SNORM:
+ return GL_SIGNED_NORMALIZED;
+ case DXGI_FORMAT_R8G8B8A8_TYPELESS:
+ break;
+ case DXGI_FORMAT_R8G8B8A8_UINT:
+ return GL_UNSIGNED_INT;
+ case DXGI_FORMAT_R8G8B8A8_UNORM:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_R8G8_B8G8_UNORM:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_R8G8_SINT:
+ return GL_INT;
+ case DXGI_FORMAT_R8G8_SNORM:
+ return GL_SIGNED_NORMALIZED;
+ case DXGI_FORMAT_R8G8_TYPELESS:
+ break;
+ case DXGI_FORMAT_R8G8_UINT:
+ return GL_UNSIGNED_INT;
+ case DXGI_FORMAT_R8G8_UNORM:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_R8_SINT:
+ return GL_INT;
+ case DXGI_FORMAT_R8_SNORM:
+ return GL_SIGNED_NORMALIZED;
+ case DXGI_FORMAT_R8_TYPELESS:
+ break;
+ case DXGI_FORMAT_R8_UINT:
+ return GL_UNSIGNED_INT;
+ case DXGI_FORMAT_R8_UNORM:
+ return GL_UNSIGNED_NORMALIZED;
+ case DXGI_FORMAT_R9G9B9E5_SHAREDEXP:
+ return GL_FLOAT;
+ case DXGI_FORMAT_UNKNOWN:
+ break;
+ case DXGI_FORMAT_X24_TYPELESS_G8_UINT:
+ return GL_UNSIGNED_INT;
+ case DXGI_FORMAT_X32_TYPELESS_G8X24_UINT:
+ return GL_UNSIGNED_INT;
+ case DXGI_FORMAT_Y210:
+ break;
+ case DXGI_FORMAT_Y216:
+ break;
+ case DXGI_FORMAT_Y410:
+ break;
+ case DXGI_FORMAT_Y416:
+ break;
+ case DXGI_FORMAT_YUY2:
+ break;
+ default:
+ break;
+ }
+
+ UNREACHABLE();
+ return GL_NONE;
+}
+
+} // namespace d3d11
+
+namespace d3d11_angle
+{
+
+const Format &GetFormat(DXGI_FORMAT dxgiFormat)
+{
+ switch (dxgiFormat)
+ {
+ case DXGI_FORMAT_420_OPAQUE:
+ break;
+ case DXGI_FORMAT_A8P8:
+ break;
+ case DXGI_FORMAT_A8_UNORM:
+ return Format::Get(Format::ID::A8_UNORM);
+ case DXGI_FORMAT_AI44:
+ break;
+ case DXGI_FORMAT_AYUV:
+ break;
+ case DXGI_FORMAT_B4G4R4A4_UNORM:
+ return Format::Get(Format::ID::B4G4R4A4_UNORM);
+ case DXGI_FORMAT_B5G5R5A1_UNORM:
+ return Format::Get(Format::ID::B5G5R5A1_UNORM);
+ case DXGI_FORMAT_B5G6R5_UNORM:
+ return Format::Get(Format::ID::B5G6R5_UNORM);
+ case DXGI_FORMAT_B8G8R8A8_TYPELESS:
+ break;
+ case DXGI_FORMAT_B8G8R8A8_UNORM:
+ return Format::Get(Format::ID::B8G8R8A8_UNORM);
+ case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB:
+ return Format::Get(Format::ID::B8G8R8A8_UNORM_SRGB);
+ case DXGI_FORMAT_B8G8R8X8_TYPELESS:
+ break;
+ case DXGI_FORMAT_B8G8R8X8_UNORM:
+ return Format::Get(Format::ID::B8G8R8X8_UNORM);
+ case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB:
+ break;
+ case DXGI_FORMAT_BC1_TYPELESS:
+ break;
+ case DXGI_FORMAT_BC1_UNORM:
+ return Format::Get(Format::ID::BC1_RGBA_UNORM_BLOCK);
+ case DXGI_FORMAT_BC1_UNORM_SRGB:
+ return Format::Get(Format::ID::BC1_RGBA_UNORM_SRGB_BLOCK);
+ case DXGI_FORMAT_BC2_TYPELESS:
+ break;
+ case DXGI_FORMAT_BC2_UNORM:
+ return Format::Get(Format::ID::BC2_RGBA_UNORM_BLOCK);
+ case DXGI_FORMAT_BC2_UNORM_SRGB:
+ return Format::Get(Format::ID::BC2_RGBA_UNORM_SRGB_BLOCK);
+ case DXGI_FORMAT_BC3_TYPELESS:
+ break;
+ case DXGI_FORMAT_BC3_UNORM:
+ return Format::Get(Format::ID::BC3_RGBA_UNORM_BLOCK);
+ case DXGI_FORMAT_BC3_UNORM_SRGB:
+ return Format::Get(Format::ID::BC3_RGBA_UNORM_SRGB_BLOCK);
+ case DXGI_FORMAT_BC4_SNORM:
+ break;
+ case DXGI_FORMAT_BC4_TYPELESS:
+ break;
+ case DXGI_FORMAT_BC4_UNORM:
+ break;
+ case DXGI_FORMAT_BC5_SNORM:
+ break;
+ case DXGI_FORMAT_BC5_TYPELESS:
+ break;
+ case DXGI_FORMAT_BC5_UNORM:
+ break;
+ case DXGI_FORMAT_BC6H_SF16:
+ break;
+ case DXGI_FORMAT_BC6H_TYPELESS:
+ break;
+ case DXGI_FORMAT_BC6H_UF16:
+ break;
+ case DXGI_FORMAT_BC7_TYPELESS:
+ break;
+ case DXGI_FORMAT_BC7_UNORM:
+ break;
+ case DXGI_FORMAT_BC7_UNORM_SRGB:
+ break;
+ case DXGI_FORMAT_D16_UNORM:
+ return Format::Get(Format::ID::D16_UNORM);
+ case DXGI_FORMAT_D24_UNORM_S8_UINT:
+ return Format::Get(Format::ID::D24_UNORM_S8_UINT);
+ case DXGI_FORMAT_D32_FLOAT:
+ return Format::Get(Format::ID::D32_FLOAT);
+ case DXGI_FORMAT_D32_FLOAT_S8X24_UINT:
+ return Format::Get(Format::ID::D32_FLOAT_S8X24_UINT);
+ case DXGI_FORMAT_G8R8_G8B8_UNORM:
+ break;
+ case DXGI_FORMAT_IA44:
+ break;
+ case DXGI_FORMAT_NV11:
+ break;
+ case DXGI_FORMAT_NV12:
+ break;
+ case DXGI_FORMAT_P010:
+ break;
+ case DXGI_FORMAT_P016:
+ break;
+ case DXGI_FORMAT_P8:
+ break;
+ case DXGI_FORMAT_R10G10B10A2_TYPELESS:
+ break;
+ case DXGI_FORMAT_R10G10B10A2_UINT:
+ return Format::Get(Format::ID::R10G10B10A2_UINT);
+ case DXGI_FORMAT_R10G10B10A2_UNORM:
+ return Format::Get(Format::ID::R10G10B10A2_UNORM);
+ case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM:
+ break;
+ case DXGI_FORMAT_R11G11B10_FLOAT:
+ return Format::Get(Format::ID::R11G11B10_FLOAT);
+ case DXGI_FORMAT_R16G16B16A16_FLOAT:
+ return Format::Get(Format::ID::R16G16B16A16_FLOAT);
+ case DXGI_FORMAT_R16G16B16A16_SINT:
+ return Format::Get(Format::ID::R16G16B16A16_SINT);
+ case DXGI_FORMAT_R16G16B16A16_SNORM:
+ return Format::Get(Format::ID::R16G16B16A16_SNORM);
+ case DXGI_FORMAT_R16G16B16A16_TYPELESS:
+ break;
+ case DXGI_FORMAT_R16G16B16A16_UINT:
+ return Format::Get(Format::ID::R16G16B16A16_UINT);
+ case DXGI_FORMAT_R16G16B16A16_UNORM:
+ return Format::Get(Format::ID::R16G16B16A16_UNORM);
+ case DXGI_FORMAT_R16G16_FLOAT:
+ return Format::Get(Format::ID::R16G16_FLOAT);
+ case DXGI_FORMAT_R16G16_SINT:
+ return Format::Get(Format::ID::R16G16_SINT);
+ case DXGI_FORMAT_R16G16_SNORM:
+ return Format::Get(Format::ID::R16G16_SNORM);
+ case DXGI_FORMAT_R16G16_TYPELESS:
+ break;
+ case DXGI_FORMAT_R16G16_UINT:
+ return Format::Get(Format::ID::R16G16_UINT);
+ case DXGI_FORMAT_R16G16_UNORM:
+ return Format::Get(Format::ID::R16G16_UNORM);
+ case DXGI_FORMAT_R16_FLOAT:
+ return Format::Get(Format::ID::R16_FLOAT);
+ case DXGI_FORMAT_R16_SINT:
+ return Format::Get(Format::ID::R16_SINT);
+ case DXGI_FORMAT_R16_SNORM:
+ return Format::Get(Format::ID::R16_SNORM);
+ case DXGI_FORMAT_R16_TYPELESS:
+ break;
+ case DXGI_FORMAT_R16_UINT:
+ return Format::Get(Format::ID::R16_UINT);
+ case DXGI_FORMAT_R16_UNORM:
+ return Format::Get(Format::ID::R16_UNORM);
+ case DXGI_FORMAT_R1_UNORM:
+ break;
+ case DXGI_FORMAT_R24G8_TYPELESS:
+ break;
+ case DXGI_FORMAT_R24_UNORM_X8_TYPELESS:
+ break;
+ case DXGI_FORMAT_R32G32B32A32_FLOAT:
+ return Format::Get(Format::ID::R32G32B32A32_FLOAT);
+ case DXGI_FORMAT_R32G32B32A32_SINT:
+ return Format::Get(Format::ID::R32G32B32A32_SINT);
+ case DXGI_FORMAT_R32G32B32A32_TYPELESS:
+ break;
+ case DXGI_FORMAT_R32G32B32A32_UINT:
+ return Format::Get(Format::ID::R32G32B32A32_UINT);
+ case DXGI_FORMAT_R32G32B32_FLOAT:
+ return Format::Get(Format::ID::R32G32B32_FLOAT);
+ case DXGI_FORMAT_R32G32B32_SINT:
+ return Format::Get(Format::ID::R32G32B32_SINT);
+ case DXGI_FORMAT_R32G32B32_TYPELESS:
+ break;
+ case DXGI_FORMAT_R32G32B32_UINT:
+ return Format::Get(Format::ID::R32G32B32_UINT);
+ case DXGI_FORMAT_R32G32_FLOAT:
+ return Format::Get(Format::ID::R32G32_FLOAT);
+ case DXGI_FORMAT_R32G32_SINT:
+ return Format::Get(Format::ID::R32G32_SINT);
+ case DXGI_FORMAT_R32G32_TYPELESS:
+ break;
+ case DXGI_FORMAT_R32G32_UINT:
+ return Format::Get(Format::ID::R32G32_UINT);
+ case DXGI_FORMAT_R32G8X24_TYPELESS:
+ break;
+ case DXGI_FORMAT_R32_FLOAT:
+ return Format::Get(Format::ID::R32_FLOAT);
+ case DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS:
+ break;
+ case DXGI_FORMAT_R32_SINT:
+ return Format::Get(Format::ID::R32_SINT);
+ case DXGI_FORMAT_R32_TYPELESS:
+ break;
+ case DXGI_FORMAT_R32_UINT:
+ return Format::Get(Format::ID::R32_UINT);
+ case DXGI_FORMAT_R8G8B8A8_SINT:
+ return Format::Get(Format::ID::R8G8B8A8_SINT);
+ case DXGI_FORMAT_R8G8B8A8_SNORM:
+ return Format::Get(Format::ID::R8G8B8A8_SNORM);
+ case DXGI_FORMAT_R8G8B8A8_TYPELESS:
+ break;
+ case DXGI_FORMAT_R8G8B8A8_UINT:
+ return Format::Get(Format::ID::R8G8B8A8_UINT);
+ case DXGI_FORMAT_R8G8B8A8_UNORM:
+ return Format::Get(Format::ID::R8G8B8A8_UNORM);
+ case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB:
+ return Format::Get(Format::ID::R8G8B8A8_UNORM_SRGB);
+ case DXGI_FORMAT_R8G8_B8G8_UNORM:
+ break;
+ case DXGI_FORMAT_R8G8_SINT:
+ return Format::Get(Format::ID::R8G8_SINT);
+ case DXGI_FORMAT_R8G8_SNORM:
+ return Format::Get(Format::ID::R8G8_SNORM);
+ case DXGI_FORMAT_R8G8_TYPELESS:
+ break;
+ case DXGI_FORMAT_R8G8_UINT:
+ return Format::Get(Format::ID::R8G8_UINT);
+ case DXGI_FORMAT_R8G8_UNORM:
+ return Format::Get(Format::ID::R8G8_UNORM);
+ case DXGI_FORMAT_R8_SINT:
+ return Format::Get(Format::ID::R8_SINT);
+ case DXGI_FORMAT_R8_SNORM:
+ return Format::Get(Format::ID::R8_SNORM);
+ case DXGI_FORMAT_R8_TYPELESS:
+ break;
+ case DXGI_FORMAT_R8_UINT:
+ return Format::Get(Format::ID::R8_UINT);
+ case DXGI_FORMAT_R8_UNORM:
+ return Format::Get(Format::ID::R8_UNORM);
+ case DXGI_FORMAT_R9G9B9E5_SHAREDEXP:
+ return Format::Get(Format::ID::R9G9B9E5_SHAREDEXP);
+ case DXGI_FORMAT_UNKNOWN:
+ return Format::Get(Format::ID::NONE);
+ case DXGI_FORMAT_X24_TYPELESS_G8_UINT:
+ break;
+ case DXGI_FORMAT_X32_TYPELESS_G8X24_UINT:
+ break;
+ case DXGI_FORMAT_Y210:
+ break;
+ case DXGI_FORMAT_Y216:
+ break;
+ case DXGI_FORMAT_Y410:
+ break;
+ case DXGI_FORMAT_Y416:
+ break;
+ case DXGI_FORMAT_YUY2:
+ break;
+ default:
+ break;
+ }
+
+ UNREACHABLE();
+ return Format::Get(Format::ID::NONE);
+}
+
+} // namespace d3d11_angle
+
+} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/dxgi_support_data.json b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/dxgi_support_data.json
index e81b4deea5..942745674f 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/dxgi_support_data.json
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/dxgi_support_data.json
@@ -8,7 +8,8 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R32G32B32A32_TYPELESS":
{
@@ -18,7 +19,8 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R32G32B32A32_FLOAT":
{
@@ -28,27 +30,30 @@
"shaderSample": "10_0check10_1always",
"renderTarget": "always",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "always"
},
"DXGI_FORMAT_R32G32B32A32_UINT":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
"shaderSample": "never",
- "renderTarget": "always",
+ "renderTarget": "10_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R32G32B32A32_SINT":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
"shaderSample": "never",
- "renderTarget": "always",
+ "renderTarget": "10_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R32G32B32_TYPELESS":
{
@@ -58,7 +63,8 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R32G32B32_FLOAT":
{
@@ -68,7 +74,8 @@
"shaderSample": "11_0check",
"renderTarget": "check",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R32G32B32_UINT":
{
@@ -78,7 +85,8 @@
"shaderSample": "never",
"renderTarget": "check",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R32G32B32_SINT":
{
@@ -88,7 +96,8 @@
"shaderSample": "never",
"renderTarget": "check",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R16G16B16A16_TYPELESS":
{
@@ -98,57 +107,63 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R16G16B16A16_FLOAT":
{
"texture2D": "always",
"texture3D": "always",
"textureCube": "always",
- "shaderSample": "10_0",
+ "shaderSample": "9_3check_10_0always",
"renderTarget": "always",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "always"
},
"DXGI_FORMAT_R16G16B16A16_UNORM":
{
"texture2D": "always",
"texture3D": "always",
"textureCube": "always",
- "shaderSample": "10_0",
+ "shaderSample": "always",
"renderTarget": "always",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "always"
},
"DXGI_FORMAT_R16G16B16A16_UINT":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
"shaderSample": "never",
- "renderTarget": "always",
+ "renderTarget": "10_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R16G16B16A16_SNORM":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
"shaderSample": "10_0",
- "renderTarget": "always",
+ "renderTarget": "10_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "10_0"
},
"DXGI_FORMAT_R16G16B16A16_SINT":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
"shaderSample": "never",
- "renderTarget": "always",
+ "renderTarget": "10_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R32G32_TYPELESS":
{
@@ -158,7 +173,8 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R32G32_FLOAT":
{
@@ -168,37 +184,41 @@
"shaderSample": "10_0check10_1always",
"renderTarget": "always",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "10_0"
},
"DXGI_FORMAT_R32G32_UINT":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
"shaderSample": "never",
- "renderTarget": "always",
+ "renderTarget": "10_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R32G32_SINT":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
"shaderSample": "never",
- "renderTarget": "always",
+ "renderTarget": "10_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R32G8X24_TYPELESS":
{
- "texture2D": "always",
+ "texture2D": "10_0",
"texture3D": "never",
- "textureCube": "always",
+ "textureCube": "10_0",
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_D32_FLOAT_S8X24_UINT":
{
@@ -208,7 +228,8 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "check",
- "depthStencil": "always"
+ "depthStencil": "10_0",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS":
{
@@ -218,7 +239,8 @@
"shaderSample": "10_0check10_1always",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_X32_TYPELESS_G8X24_UINT":
{
@@ -228,47 +250,52 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R10G10B10A2_TYPELESS":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R10G10B10A2_UNORM":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
"shaderSample": "10_0",
- "renderTarget": "always",
+ "renderTarget": "10_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "10_0"
},
"DXGI_FORMAT_R10G10B10A2_UINT":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
"shaderSample": "never",
- "renderTarget": "always",
+ "renderTarget": "10_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R11G11B10_FLOAT":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
"shaderSample": "10_0",
- "renderTarget": "always",
+ "renderTarget": "10_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "10_0"
},
"DXGI_FORMAT_R8G8B8A8_TYPELESS":
{
@@ -278,57 +305,63 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R8G8B8A8_UNORM":
{
"texture2D": "always",
"texture3D": "always",
"textureCube": "always",
- "shaderSample": "10_0",
+ "shaderSample": "always",
"renderTarget": "always",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "always"
},
"DXGI_FORMAT_R8G8B8A8_UNORM_SRGB":
{
"texture2D": "always",
"texture3D": "always",
"textureCube": "always",
- "shaderSample": "10_0",
+ "shaderSample": "always",
"renderTarget": "always",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "always"
},
"DXGI_FORMAT_R8G8B8A8_UINT":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
"shaderSample": "never",
- "renderTarget": "always",
+ "renderTarget": "10_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R8G8B8A8_SNORM":
{
"texture2D": "always",
"texture3D": "always",
"textureCube": "always",
- "shaderSample": "10_0",
+ "shaderSample": "always",
"renderTarget": "always",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "10_0"
},
"DXGI_FORMAT_R8G8B8A8_SINT":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
"shaderSample": "never",
- "renderTarget": "always",
+ "renderTarget": "10_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R16G16_TYPELESS":
{
@@ -338,7 +371,8 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R16G16_FLOAT":
{
@@ -348,57 +382,63 @@
"shaderSample": "10_0",
"renderTarget": "always",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "always"
},
"DXGI_FORMAT_R16G16_UNORM":
{
"texture2D": "always",
"texture3D": "always",
"textureCube": "always",
- "shaderSample": "10_0",
+ "shaderSample": "always",
"renderTarget": "always",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "always"
},
"DXGI_FORMAT_R16G16_UINT":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
"shaderSample": "never",
- "renderTarget": "always",
+ "renderTarget": "10_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R16G16_SNORM":
{
"texture2D": "always",
"texture3D": "always",
"textureCube": "always",
- "shaderSample": "10_0",
+ "shaderSample": "always",
"renderTarget": "always",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "10_0"
},
"DXGI_FORMAT_R16G16_SINT":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
"shaderSample": "never",
- "renderTarget": "always",
+ "renderTarget": "10_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R32_TYPELESS":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_D32_FLOAT":
{
@@ -408,7 +448,8 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "check",
- "depthStencil": "always"
+ "depthStencil": "10_0",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R32_FLOAT":
{
@@ -418,27 +459,30 @@
"shaderSample": "10_0check10_1always",
"renderTarget": "always",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "always"
},
"DXGI_FORMAT_R32_UINT":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
"shaderSample": "never",
- "renderTarget": "always",
+ "renderTarget": "10_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R32_SINT":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
"shaderSample": "never",
- "renderTarget": "always",
+ "renderTarget": "10_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R24G8_TYPELESS":
{
@@ -448,7 +492,8 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_D24_UNORM_S8_UINT":
{
@@ -468,7 +513,8 @@
"shaderSample": "10_0check10_1always",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_X24_TYPELESS_G8_UINT":
{
@@ -478,7 +524,8 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R8G8_TYPELESS":
{
@@ -488,47 +535,52 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R8G8_UNORM":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
- "shaderSample": "10_0",
- "renderTarget": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
+ "shaderSample": "9_3check_10_0always",
+ "renderTarget": "9_3check_10_0always",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "10_0"
},
"DXGI_FORMAT_R8G8_UINT":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
"shaderSample": "never",
- "renderTarget": "always",
+ "renderTarget": "10_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R8G8_SNORM":
{
"texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
- "shaderSample": "10_0",
- "renderTarget": "always",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
+ "shaderSample": "always",
+ "renderTarget": "10_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "10_0"
},
"DXGI_FORMAT_R8G8_SINT":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
"shaderSample": "never",
- "renderTarget": "always",
+ "renderTarget": "10_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R16_TYPELESS":
{
@@ -538,17 +590,19 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R16_FLOAT":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
"shaderSample": "10_0",
- "renderTarget": "always",
+ "renderTarget": "10_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "10_0"
},
"DXGI_FORMAT_D16_UNORM":
{
@@ -558,47 +612,52 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "check",
- "depthStencil": "always"
+ "depthStencil": "always",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R16_UNORM":
{
"texture2D": "always",
"texture3D": "always",
"textureCube": "always",
- "shaderSample": "10_0",
- "renderTarget": "always",
+ "shaderSample": "always",
+ "renderTarget": "10_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "10_0"
},
"DXGI_FORMAT_R16_UINT":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
"shaderSample": "never",
- "renderTarget": "always",
+ "renderTarget": "10_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R16_SNORM":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
"shaderSample": "10_0",
- "renderTarget": "always",
+ "renderTarget": "10_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "10_0"
},
"DXGI_FORMAT_R16_SINT":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
"shaderSample": "never",
- "renderTarget": "always",
+ "renderTarget": "10_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R8_TYPELESS":
{
@@ -608,47 +667,52 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R8_UNORM":
{
"texture2D": "always",
"texture3D": "always",
"textureCube": "always",
- "shaderSample": "10_0",
- "renderTarget": "always",
+ "shaderSample": "always",
+ "renderTarget": "9_3check_10_0always",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "10_0"
},
"DXGI_FORMAT_R8_UINT":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
"shaderSample": "never",
- "renderTarget": "always",
+ "renderTarget": "10_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R8_SNORM":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
"shaderSample": "10_0",
- "renderTarget": "always",
+ "renderTarget": "10_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "10_0"
},
"DXGI_FORMAT_R8_SINT":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
"shaderSample": "never",
- "renderTarget": "always",
+ "renderTarget": "10_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_A8_UNORM":
{
@@ -658,7 +722,8 @@
"shaderSample": "10_0",
"renderTarget": "always",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "10_0"
},
"DXGI_FORMAT_R1_UNORM":
{
@@ -668,17 +733,19 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R9G9B9E5_SHAREDEXP":
{
- "texture2D": "always",
- "texture3D": "always",
- "textureCube": "always",
+ "texture2D": "10_0",
+ "texture3D": "10_0",
+ "textureCube": "10_0",
"shaderSample": "10_0",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R8G8_B8G8_UNORM":
{
@@ -688,7 +755,8 @@
"shaderSample": "10_0",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_G8R8_G8B8_UNORM":
{
@@ -698,7 +766,8 @@
"shaderSample": "10_0",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_BC1_TYPELESS":
{
@@ -708,27 +777,30 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_BC1_UNORM":
{
"texture2D": "always",
"texture3D": "always",
"textureCube": "always",
- "shaderSample": "10_0",
+ "shaderSample": "always",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_BC1_UNORM_SRGB":
{
"texture2D": "always",
"texture3D": "always",
"textureCube": "always",
- "shaderSample": "10_0",
+ "shaderSample": "always",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_BC2_TYPELESS":
{
@@ -738,27 +810,30 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_BC2_UNORM":
{
"texture2D": "always",
"texture3D": "always",
"textureCube": "always",
- "shaderSample": "10_0",
+ "shaderSample": "always",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_BC2_UNORM_SRGB":
{
"texture2D": "always",
"texture3D": "always",
"textureCube": "always",
- "shaderSample": "10_0",
+ "shaderSample": "always",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_BC3_TYPELESS":
{
@@ -768,27 +843,30 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_BC3_UNORM":
{
"texture2D": "always",
"texture3D": "always",
"textureCube": "always",
- "shaderSample": "10_0",
+ "shaderSample": "always",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_BC3_UNORM_SRGB":
{
"texture2D": "always",
"texture3D": "always",
"textureCube": "always",
- "shaderSample": "10_0",
+ "shaderSample": "always",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_BC4_TYPELESS":
{
@@ -798,7 +876,8 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_BC4_UNORM":
{
@@ -808,7 +887,8 @@
"shaderSample": "10_0",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_BC4_SNORM":
{
@@ -818,7 +898,8 @@
"shaderSample": "10_0",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_BC5_TYPELESS":
{
@@ -828,7 +909,8 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_BC5_UNORM":
{
@@ -838,7 +920,8 @@
"shaderSample": "10_0",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_BC5_SNORM":
{
@@ -848,7 +931,8 @@
"shaderSample": "10_0",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_B5G6R5_UNORM":
{
@@ -858,7 +942,8 @@
"shaderSample": "dxgi1_2",
"renderTarget": "dxgi1_2",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "dxgi1_2"
},
"DXGI_FORMAT_B5G5R5A1_UNORM":
{
@@ -868,17 +953,19 @@
"shaderSample": "dxgi1_2",
"renderTarget": "check",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "dxgi1_2"
},
"DXGI_FORMAT_B8G8R8A8_UNORM":
{
"texture2D": "check",
"texture3D": "check",
"textureCube": "check",
- "shaderSample": "10_0check11_0always",
- "renderTarget": "10_0check11_0always",
+ "shaderSample": "9_3always_10_0check11_0always",
+ "renderTarget": "9_3always_10_0check11_0always",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "always"
},
"DXGI_FORMAT_B8G8R8X8_UNORM":
{
@@ -888,7 +975,8 @@
"shaderSample": "10_0check11_0always",
"renderTarget": "11_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM":
{
@@ -898,7 +986,8 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_B8G8R8A8_TYPELESS":
{
@@ -908,7 +997,8 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_B8G8R8A8_UNORM_SRGB":
{
@@ -918,7 +1008,8 @@
"shaderSample": "10_0check11_0always",
"renderTarget": "11_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_B8G8R8X8_TYPELESS":
{
@@ -928,7 +1019,8 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_B8G8R8X8_UNORM_SRGB":
{
@@ -938,7 +1030,8 @@
"shaderSample": "10_0check11_0always",
"renderTarget": "11_0",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_BC6H_TYPELESS":
{
@@ -948,7 +1041,8 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_BC6H_UF16":
{
@@ -958,7 +1052,8 @@
"shaderSample": "11_0",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_BC6H_SF16":
{
@@ -968,7 +1063,8 @@
"shaderSample": "11_0",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_BC7_TYPELESS":
{
@@ -978,7 +1074,8 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_BC7_UNORM":
{
@@ -988,7 +1085,8 @@
"shaderSample": "11_0",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_BC7_UNORM_SRGB":
{
@@ -998,7 +1096,8 @@
"shaderSample": "11_0",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_AYUV":
{
@@ -1008,7 +1107,8 @@
"shaderSample": "11_1",
"renderTarget": "11_1",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_Y410":
{
@@ -1018,7 +1118,8 @@
"shaderSample": "11_1",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_Y416":
{
@@ -1028,7 +1129,8 @@
"shaderSample": "11_1",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_NV12":
{
@@ -1038,7 +1140,8 @@
"shaderSample": "11_1",
"renderTarget": "11_1",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_P010":
{
@@ -1048,7 +1151,8 @@
"shaderSample": "11_1",
"renderTarget": "11_1",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_P016":
{
@@ -1058,7 +1162,8 @@
"shaderSample": "11_1",
"renderTarget": "11_1",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_420_OPAQUE":
{
@@ -1068,7 +1173,8 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_YUY2":
{
@@ -1078,7 +1184,8 @@
"shaderSample": "11_1",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_Y210":
{
@@ -1088,7 +1195,8 @@
"shaderSample": "11_1",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_Y216":
{
@@ -1098,7 +1206,8 @@
"shaderSample": "11_1",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_NV11":
{
@@ -1108,7 +1217,8 @@
"shaderSample": "11_1",
"renderTarget": "11_1",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_AI44":
{
@@ -1118,7 +1228,8 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_IA44":
{
@@ -1128,7 +1239,8 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_P8":
{
@@ -1138,7 +1250,8 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_A8P8":
{
@@ -1148,7 +1261,8 @@
"shaderSample": "never",
"renderTarget": "never",
"multisampleRT": "never",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "never"
},
"DXGI_FORMAT_B4G4R4A4_UNORM":
{
@@ -1158,7 +1272,8 @@
"shaderSample": "dxgi1_2",
"renderTarget": "check",
"multisampleRT": "check",
- "depthStencil": "never"
+ "depthStencil": "never",
+ "mipAutoGen": "dxgi1_2"
}
}
]
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/dxgi_support_table.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/dxgi_support_table.cpp
index cbc36445e6..4d7e46bdf2 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/dxgi_support_table.cpp
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/dxgi_support_table.cpp
@@ -26,205 +26,205 @@ namespace d3d11
#define F_RT D3D11_FORMAT_SUPPORT_RENDER_TARGET
#define F_MS D3D11_FORMAT_SUPPORT_MULTISAMPLE_RENDERTARGET
#define F_DS D3D11_FORMAT_SUPPORT_DEPTH_STENCIL
+#define F_MIPGEN D3D11_FORMAT_SUPPORT_MIP_AUTOGEN
namespace
{
const DXGISupport &GetDefaultSupport()
{
- static UINT AllSupportFlags = D3D11_FORMAT_SUPPORT_TEXTURE2D |
- D3D11_FORMAT_SUPPORT_TEXTURE3D |
- D3D11_FORMAT_SUPPORT_TEXTURECUBE |
- D3D11_FORMAT_SUPPORT_SHADER_SAMPLE |
- D3D11_FORMAT_SUPPORT_RENDER_TARGET |
- D3D11_FORMAT_SUPPORT_MULTISAMPLE_RENDERTARGET |
- D3D11_FORMAT_SUPPORT_DEPTH_STENCIL;
+ static UINT AllSupportFlags =
+ D3D11_FORMAT_SUPPORT_TEXTURE2D | D3D11_FORMAT_SUPPORT_TEXTURE3D |
+ D3D11_FORMAT_SUPPORT_TEXTURECUBE | D3D11_FORMAT_SUPPORT_SHADER_SAMPLE |
+ D3D11_FORMAT_SUPPORT_RENDER_TARGET | D3D11_FORMAT_SUPPORT_MULTISAMPLE_RENDERTARGET |
+ D3D11_FORMAT_SUPPORT_DEPTH_STENCIL | D3D11_FORMAT_SUPPORT_MIP_AUTOGEN;
static const DXGISupport defaultSupport(0, 0, AllSupportFlags);
return defaultSupport;
}
-const DXGISupport &GetDXGISupport_10_0(DXGI_FORMAT dxgiFormat)
+const DXGISupport &GetDXGISupport_9_3(DXGI_FORMAT dxgiFormat)
{
+ // clang-format off
switch (dxgiFormat)
{
case DXGI_FORMAT_420_OPAQUE:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_A8P8:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_A8_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_AI44:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_AYUV:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_RT | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN, F_MS);
return info;
}
case DXGI_FORMAT_B4G4R4A4_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS, F_MS | F_RT);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_SAMPLE, F_DS, F_MS | F_RT);
return info;
}
case DXGI_FORMAT_B5G5R5A1_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS, F_MS | F_RT);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_SAMPLE, F_DS, F_MS | F_RT);
return info;
}
case DXGI_FORMAT_B5G6R5_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_B8G8R8A8_TYPELESS:
{
- static const DXGISupport info(0, F_DS | F_MS | F_RT | F_SAMPLE, F_2D | F_3D | F_CUBE);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, F_2D | F_3D | F_CUBE);
return info;
}
case DXGI_FORMAT_B8G8R8A8_UNORM:
{
- static const DXGISupport info(0, F_DS, F_2D | F_3D | F_CUBE | F_MS | F_RT | F_SAMPLE);
+ static const DXGISupport info(F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_2D | F_3D | F_CUBE | F_MS);
return info;
}
case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB:
{
- static const DXGISupport info(0, F_DS, F_2D | F_3D | F_CUBE | F_MS | F_SAMPLE);
+ static const DXGISupport info(0, F_DS | F_MIPGEN, F_2D | F_3D | F_CUBE | F_MS);
return info;
}
case DXGI_FORMAT_B8G8R8X8_TYPELESS:
{
- static const DXGISupport info(0, F_DS | F_MS | F_RT | F_SAMPLE, F_2D | F_3D | F_CUBE);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, F_2D | F_3D | F_CUBE);
return info;
}
case DXGI_FORMAT_B8G8R8X8_UNORM:
{
- static const DXGISupport info(0, F_DS, F_2D | F_3D | F_CUBE | F_MS | F_SAMPLE);
+ static const DXGISupport info(0, F_DS | F_MIPGEN, F_2D | F_3D | F_CUBE | F_MS);
return info;
}
case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB:
{
- static const DXGISupport info(0, F_DS, F_2D | F_3D | F_CUBE | F_MS | F_SAMPLE);
+ static const DXGISupport info(0, F_DS | F_MIPGEN, F_2D | F_3D | F_CUBE | F_MS);
return info;
}
case DXGI_FORMAT_BC1_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_BC1_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC1_UNORM_SRGB:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC2_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_BC2_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC2_UNORM_SRGB:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC3_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_BC3_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC3_UNORM_SRGB:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC4_SNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC4_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_BC4_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC5_SNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC5_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_BC5_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC6H_SF16:
{
- static const DXGISupport info(0, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC6H_TYPELESS:
{
- static const DXGISupport info(0, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_BC6H_UF16:
{
- static const DXGISupport info(0, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC7_TYPELESS:
{
- static const DXGISupport info(0, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_BC7_UNORM:
{
- static const DXGISupport info(0, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC7_UNORM_SRGB:
{
- static const DXGISupport info(0, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_D16_UNORM:
{
- static const DXGISupport info(F_2D | F_CUBE | F_DS, F_3D | F_RT | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_CUBE | F_DS, F_3D | F_MIPGEN | F_RT | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_D24_UNORM_S8_UINT:
@@ -234,112 +234,112 @@ const DXGISupport &GetDXGISupport_10_0(DXGI_FORMAT dxgiFormat)
}
case DXGI_FORMAT_D32_FLOAT:
{
- static const DXGISupport info(F_2D | F_CUBE | F_DS, F_3D | F_RT | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_CUBE, F_3D | F_MIPGEN | F_RT | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_D32_FLOAT_S8X24_UINT:
{
- static const DXGISupport info(F_2D | F_CUBE | F_DS, F_3D | F_RT | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_CUBE, F_3D | F_MIPGEN | F_RT | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_G8R8_G8B8_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_IA44:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_NV11:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_RT | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN, F_MS);
return info;
}
case DXGI_FORMAT_NV12:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_RT | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN, F_MS);
return info;
}
case DXGI_FORMAT_P010:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_RT | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN, F_MS);
return info;
}
case DXGI_FORMAT_P016:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_RT | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN, F_MS);
return info;
}
case DXGI_FORMAT_P8:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R10G10B10A2_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R10G10B10A2_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R10G10B10A2_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(0, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM:
{
- static const DXGISupport info(0, F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, F_2D | F_3D);
+ static const DXGISupport info(0, F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, F_2D | F_3D);
return info;
}
case DXGI_FORMAT_R11G11B10_FLOAT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(0, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R16G16B16A16_FLOAT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT, F_DS, F_MS | F_SAMPLE);
return info;
}
case DXGI_FORMAT_R16G16B16A16_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R16G16B16A16_SNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(0, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R16G16B16A16_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R16G16B16A16_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R16G16B16A16_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R16G16_FLOAT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R16G16_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R16G16_SNORM:
@@ -349,157 +349,157 @@ const DXGISupport &GetDXGISupport_10_0(DXGI_FORMAT dxgiFormat)
}
case DXGI_FORMAT_R16G16_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R16G16_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R16G16_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R16_FLOAT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(0, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R16_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R16_SNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(0, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R16_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R16_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R16_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R1_UNORM:
{
- static const DXGISupport info(F_2D, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R24G8_TYPELESS:
{
- static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R24_UNORM_X8_TYPELESS:
{
- static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MS | F_RT, F_SAMPLE);
+ static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_R32G32B32A32_FLOAT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS, F_MS | F_SAMPLE);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R32G32B32A32_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R32G32B32A32_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R32G32B32A32_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R32G32B32_FLOAT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS, F_MS | F_RT);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN, F_MS | F_RT);
return info;
}
case DXGI_FORMAT_R32G32B32_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_SAMPLE, F_MS | F_RT);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_SAMPLE, F_MS | F_RT);
return info;
}
case DXGI_FORMAT_R32G32B32_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R32G32B32_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_SAMPLE, F_MS | F_RT);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_SAMPLE, F_MS | F_RT);
return info;
}
case DXGI_FORMAT_R32G32_FLOAT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS, F_MS | F_SAMPLE);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R32G32_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R32G32_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R32G32_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R32G8X24_TYPELESS:
{
- static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_3D | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R32_FLOAT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS, F_MS | F_SAMPLE);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS:
{
- static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MS | F_RT, F_SAMPLE);
+ static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_R32_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R32_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R32_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R8G8B8A8_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R8G8B8A8_SNORM:
@@ -509,122 +509,122 @@ const DXGISupport &GetDXGISupport_10_0(DXGI_FORMAT dxgiFormat)
}
case DXGI_FORMAT_R8G8B8A8_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R8G8B8A8_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R8G8B8A8_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R8G8_B8G8_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_R8G8_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R8G8_SNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R8G8_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R8G8_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R8G8_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(0, F_DS, F_MS | F_RT | F_SAMPLE);
return info;
}
case DXGI_FORMAT_R8_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R8_SNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(0, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R8_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R8_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R8_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS, F_MS | F_RT);
return info;
}
case DXGI_FORMAT_R9G9B9E5_SHAREDEXP:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_UNKNOWN:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_X24_TYPELESS_G8_UINT:
{
- static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_X32_TYPELESS_G8X24_UINT:
{
- static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_Y210:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_Y216:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_Y410:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_Y416:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_YUY2:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
@@ -632,190 +632,192 @@ const DXGISupport &GetDXGISupport_10_0(DXGI_FORMAT dxgiFormat)
UNREACHABLE();
return GetDefaultSupport();
}
+ // clang-format on
}
-const DXGISupport &GetDXGISupport_10_1(DXGI_FORMAT dxgiFormat)
+const DXGISupport &GetDXGISupport_10_0(DXGI_FORMAT dxgiFormat)
{
+ // clang-format off
switch (dxgiFormat)
{
case DXGI_FORMAT_420_OPAQUE:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_A8P8:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_A8_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_AI44:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_AYUV:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_RT | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN, F_MS);
return info;
}
case DXGI_FORMAT_B4G4R4A4_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS, F_MS | F_RT);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_SAMPLE, F_DS, F_MS | F_RT);
return info;
}
case DXGI_FORMAT_B5G5R5A1_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS, F_MS | F_RT);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_SAMPLE, F_DS, F_MS | F_RT);
return info;
}
case DXGI_FORMAT_B5G6R5_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_B8G8R8A8_TYPELESS:
{
- static const DXGISupport info(0, F_DS | F_MS | F_RT | F_SAMPLE, F_2D | F_3D | F_CUBE);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, F_2D | F_3D | F_CUBE);
return info;
}
case DXGI_FORMAT_B8G8R8A8_UNORM:
{
- static const DXGISupport info(0, F_DS, F_2D | F_3D | F_CUBE | F_MS | F_RT | F_SAMPLE);
+ static const DXGISupport info(F_MIPGEN, F_DS, F_2D | F_3D | F_CUBE | F_MS | F_RT | F_SAMPLE);
return info;
}
case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB:
{
- static const DXGISupport info(0, F_DS, F_2D | F_3D | F_CUBE | F_MS | F_SAMPLE);
+ static const DXGISupport info(0, F_DS | F_MIPGEN, F_2D | F_3D | F_CUBE | F_MS | F_SAMPLE);
return info;
}
case DXGI_FORMAT_B8G8R8X8_TYPELESS:
{
- static const DXGISupport info(0, F_DS | F_MS | F_RT | F_SAMPLE, F_2D | F_3D | F_CUBE);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, F_2D | F_3D | F_CUBE);
return info;
}
case DXGI_FORMAT_B8G8R8X8_UNORM:
{
- static const DXGISupport info(0, F_DS, F_2D | F_3D | F_CUBE | F_MS | F_SAMPLE);
+ static const DXGISupport info(0, F_DS | F_MIPGEN, F_2D | F_3D | F_CUBE | F_MS | F_SAMPLE);
return info;
}
case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB:
{
- static const DXGISupport info(0, F_DS, F_2D | F_3D | F_CUBE | F_MS | F_SAMPLE);
+ static const DXGISupport info(0, F_DS | F_MIPGEN, F_2D | F_3D | F_CUBE | F_MS | F_SAMPLE);
return info;
}
case DXGI_FORMAT_BC1_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_BC1_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC1_UNORM_SRGB:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC2_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_BC2_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC2_UNORM_SRGB:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC3_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_BC3_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC3_UNORM_SRGB:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC4_SNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC4_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_BC4_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC5_SNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC5_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_BC5_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC6H_SF16:
{
- static const DXGISupport info(0, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC6H_TYPELESS:
{
- static const DXGISupport info(0, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_BC6H_UF16:
{
- static const DXGISupport info(0, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC7_TYPELESS:
{
- static const DXGISupport info(0, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_BC7_UNORM:
{
- static const DXGISupport info(0, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC7_UNORM_SRGB:
{
- static const DXGISupport info(0, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_D16_UNORM:
{
- static const DXGISupport info(F_2D | F_CUBE | F_DS, F_3D | F_RT | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_CUBE | F_DS, F_3D | F_MIPGEN | F_RT | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_D24_UNORM_S8_UINT:
@@ -825,397 +827,990 @@ const DXGISupport &GetDXGISupport_10_1(DXGI_FORMAT dxgiFormat)
}
case DXGI_FORMAT_D32_FLOAT:
{
- static const DXGISupport info(F_2D | F_CUBE | F_DS, F_3D | F_RT | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_CUBE | F_DS, F_3D | F_MIPGEN | F_RT | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_D32_FLOAT_S8X24_UINT:
{
+ static const DXGISupport info(F_2D | F_CUBE | F_DS, F_3D | F_MIPGEN | F_RT | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_G8R8_G8B8_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_IA44:
+ {
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_NV11:
+ {
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_NV12:
+ {
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_P010:
+ {
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_P016:
+ {
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_P8:
+ {
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R10G10B10A2_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R10G10B10A2_UINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R10G10B10A2_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM:
+ {
+ static const DXGISupport info(0, F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, F_2D | F_3D);
+ return info;
+ }
+ case DXGI_FORMAT_R11G11B10_FLOAT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16G16B16A16_FLOAT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16G16B16A16_SINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16G16B16A16_SNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16G16B16A16_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R16G16B16A16_UINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16G16B16A16_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16G16_FLOAT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16G16_SINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16G16_SNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16G16_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R16G16_UINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16G16_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16_FLOAT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16_SINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16_SNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R16_UINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R1_UNORM:
+ {
+ static const DXGISupport info(F_2D, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R24G8_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R24_UNORM_X8_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT, F_SAMPLE);
+ return info;
+ }
+ case DXGI_FORMAT_R32G32B32A32_FLOAT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT, F_DS, F_MS | F_SAMPLE);
+ return info;
+ }
+ case DXGI_FORMAT_R32G32B32A32_SINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R32G32B32A32_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R32G32B32A32_UINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R32G32B32_FLOAT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN, F_MS | F_RT);
+ return info;
+ }
+ case DXGI_FORMAT_R32G32B32_SINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_SAMPLE, F_MS | F_RT);
+ return info;
+ }
+ case DXGI_FORMAT_R32G32B32_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R32G32B32_UINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_SAMPLE, F_MS | F_RT);
+ return info;
+ }
+ case DXGI_FORMAT_R32G32_FLOAT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT, F_DS, F_MS | F_SAMPLE);
+ return info;
+ }
+ case DXGI_FORMAT_R32G32_SINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R32G32_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R32G32_UINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R32G8X24_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R32_FLOAT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT, F_DS, F_MS | F_SAMPLE);
+ return info;
+ }
+ case DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT, F_SAMPLE);
+ return info;
+ }
+ case DXGI_FORMAT_R32_SINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R32_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R32_UINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R8G8B8A8_SINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R8G8B8A8_SNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R8G8B8A8_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R8G8B8A8_UINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R8G8B8A8_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R8G8_B8G8_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R8G8_SINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R8G8_SNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R8G8_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R8G8_UINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R8G8_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R8_SINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R8_SNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R8_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R8_UINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R8_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R9G9B9E5_SHAREDEXP:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_UNKNOWN:
+ {
+ static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_X24_TYPELESS_G8_UINT:
+ {
+ static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_X32_TYPELESS_G8X24_UINT:
+ {
+ static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_Y210:
+ {
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_Y216:
+ {
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_Y410:
+ {
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_Y416:
+ {
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_YUY2:
+ {
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+
+ default:
+ UNREACHABLE();
+ return GetDefaultSupport();
+ }
+ // clang-format on
+}
+
+const DXGISupport &GetDXGISupport_10_1(DXGI_FORMAT dxgiFormat)
+{
+ // clang-format off
+ switch (dxgiFormat)
+ {
+ case DXGI_FORMAT_420_OPAQUE:
+ {
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_A8P8:
+ {
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_A8_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_AI44:
+ {
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_AYUV:
+ {
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_B4G4R4A4_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_SAMPLE, F_DS, F_MS | F_RT);
+ return info;
+ }
+ case DXGI_FORMAT_B5G5R5A1_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_SAMPLE, F_DS, F_MS | F_RT);
+ return info;
+ }
+ case DXGI_FORMAT_B5G6R5_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_B8G8R8A8_TYPELESS:
+ {
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, F_2D | F_3D | F_CUBE);
+ return info;
+ }
+ case DXGI_FORMAT_B8G8R8A8_UNORM:
+ {
+ static const DXGISupport info(F_MIPGEN, F_DS, F_2D | F_3D | F_CUBE | F_MS | F_RT | F_SAMPLE);
+ return info;
+ }
+ case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB:
+ {
+ static const DXGISupport info(0, F_DS | F_MIPGEN, F_2D | F_3D | F_CUBE | F_MS | F_SAMPLE);
+ return info;
+ }
+ case DXGI_FORMAT_B8G8R8X8_TYPELESS:
+ {
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, F_2D | F_3D | F_CUBE);
+ return info;
+ }
+ case DXGI_FORMAT_B8G8R8X8_UNORM:
+ {
+ static const DXGISupport info(0, F_DS | F_MIPGEN, F_2D | F_3D | F_CUBE | F_MS | F_SAMPLE);
+ return info;
+ }
+ case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB:
+ {
+ static const DXGISupport info(0, F_DS | F_MIPGEN, F_2D | F_3D | F_CUBE | F_MS | F_SAMPLE);
+ return info;
+ }
+ case DXGI_FORMAT_BC1_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC1_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC1_UNORM_SRGB:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC2_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC2_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC2_UNORM_SRGB:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC3_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC3_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC3_UNORM_SRGB:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC4_SNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC4_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC4_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC5_SNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC5_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC5_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC6H_SF16:
+ {
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC6H_TYPELESS:
+ {
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC6H_UF16:
+ {
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC7_TYPELESS:
+ {
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC7_UNORM:
+ {
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC7_UNORM_SRGB:
+ {
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_D16_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_CUBE | F_DS, F_3D | F_MIPGEN | F_RT | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_D24_UNORM_S8_UINT:
+ {
static const DXGISupport info(F_2D | F_CUBE | F_DS, F_3D | F_RT | F_SAMPLE, F_MS);
return info;
}
+ case DXGI_FORMAT_D32_FLOAT:
+ {
+ static const DXGISupport info(F_2D | F_CUBE | F_DS, F_3D | F_MIPGEN | F_RT | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_D32_FLOAT_S8X24_UINT:
+ {
+ static const DXGISupport info(F_2D | F_CUBE | F_DS, F_3D | F_MIPGEN | F_RT | F_SAMPLE, F_MS);
+ return info;
+ }
case DXGI_FORMAT_G8R8_G8B8_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_IA44:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_NV11:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_RT | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN, F_MS);
return info;
}
case DXGI_FORMAT_NV12:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_RT | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN, F_MS);
return info;
}
case DXGI_FORMAT_P010:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_RT | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN, F_MS);
return info;
}
case DXGI_FORMAT_P016:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_RT | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN, F_MS);
return info;
}
case DXGI_FORMAT_P8:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R10G10B10A2_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R10G10B10A2_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R10G10B10A2_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM:
{
- static const DXGISupport info(0, F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, F_2D | F_3D);
+ static const DXGISupport info(0, F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, F_2D | F_3D);
return info;
}
case DXGI_FORMAT_R11G11B10_FLOAT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R16G16B16A16_FLOAT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R16G16B16A16_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R16G16B16A16_SNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R16G16B16A16_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R16G16B16A16_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R16G16B16A16_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R16G16_FLOAT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R16G16_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R16G16_SNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R16G16_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R16G16_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R16G16_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R16_FLOAT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R16_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R16_SNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R16_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R16_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R16_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R1_UNORM:
{
- static const DXGISupport info(F_2D, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R24G8_TYPELESS:
{
- static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R24_UNORM_X8_TYPELESS:
{
- static const DXGISupport info(F_2D | F_CUBE | F_SAMPLE, F_3D | F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_CUBE | F_SAMPLE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_R32G32B32A32_FLOAT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R32G32B32A32_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R32G32B32A32_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R32G32B32A32_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R32G32B32_FLOAT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS, F_MS | F_RT);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN, F_MS | F_RT);
return info;
}
case DXGI_FORMAT_R32G32B32_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_SAMPLE, F_MS | F_RT);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_SAMPLE, F_MS | F_RT);
return info;
}
case DXGI_FORMAT_R32G32B32_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R32G32B32_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_SAMPLE, F_MS | F_RT);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_SAMPLE, F_MS | F_RT);
return info;
}
case DXGI_FORMAT_R32G32_FLOAT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R32G32_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R32G32_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R32G32_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R32G8X24_TYPELESS:
{
- static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R32_FLOAT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS:
{
- static const DXGISupport info(F_2D | F_CUBE | F_SAMPLE, F_3D | F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_CUBE | F_SAMPLE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_R32_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R32_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R32_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R8G8B8A8_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R8G8B8A8_SNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R8G8B8A8_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R8G8B8A8_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R8G8B8A8_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R8G8_B8G8_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_R8G8_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R8G8_SNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R8G8_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R8G8_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R8G8_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R8_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R8_SNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R8_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R8_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R8_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R9G9B9E5_SHAREDEXP:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_UNKNOWN:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_X24_TYPELESS_G8_UINT:
{
- static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_X32_TYPELESS_G8X24_UINT:
{
- static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_Y210:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_Y216:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_Y410:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_Y416:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_YUY2:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
@@ -1223,190 +1818,192 @@ const DXGISupport &GetDXGISupport_10_1(DXGI_FORMAT dxgiFormat)
UNREACHABLE();
return GetDefaultSupport();
}
+ // clang-format on
}
const DXGISupport &GetDXGISupport_11_0(DXGI_FORMAT dxgiFormat)
{
+ // clang-format off
switch (dxgiFormat)
{
case DXGI_FORMAT_420_OPAQUE:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_A8P8:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_A8_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_AI44:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_AYUV:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_RT | F_SAMPLE, F_MS);
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN, F_MS);
return info;
}
case DXGI_FORMAT_B4G4R4A4_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS, F_MS | F_RT);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_SAMPLE, F_DS, F_MS | F_RT);
return info;
}
case DXGI_FORMAT_B5G5R5A1_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS, F_MS | F_RT);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_SAMPLE, F_DS, F_MS | F_RT);
return info;
}
case DXGI_FORMAT_B5G6R5_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_B8G8R8A8_TYPELESS:
{
- static const DXGISupport info(0, F_DS | F_MS | F_RT | F_SAMPLE, F_2D | F_3D | F_CUBE);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, F_2D | F_3D | F_CUBE);
return info;
}
case DXGI_FORMAT_B8G8R8A8_UNORM:
{
- static const DXGISupport info(F_RT | F_SAMPLE, F_DS, F_2D | F_3D | F_CUBE | F_MS);
+ static const DXGISupport info(F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_2D | F_3D | F_CUBE | F_MS);
return info;
}
case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB:
{
- static const DXGISupport info(F_RT | F_SAMPLE, F_DS, F_2D | F_3D | F_CUBE | F_MS);
+ static const DXGISupport info(F_RT | F_SAMPLE, F_DS | F_MIPGEN, F_2D | F_3D | F_CUBE | F_MS);
return info;
}
case DXGI_FORMAT_B8G8R8X8_TYPELESS:
{
- static const DXGISupport info(0, F_DS | F_MS | F_RT | F_SAMPLE, F_2D | F_3D | F_CUBE);
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, F_2D | F_3D | F_CUBE);
return info;
}
case DXGI_FORMAT_B8G8R8X8_UNORM:
{
- static const DXGISupport info(F_RT | F_SAMPLE, F_DS, F_2D | F_3D | F_CUBE | F_MS);
+ static const DXGISupport info(F_RT | F_SAMPLE, F_DS | F_MIPGEN, F_2D | F_3D | F_CUBE | F_MS);
return info;
}
case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB:
{
- static const DXGISupport info(F_RT | F_SAMPLE, F_DS, F_2D | F_3D | F_CUBE | F_MS);
+ static const DXGISupport info(F_RT | F_SAMPLE, F_DS | F_MIPGEN, F_2D | F_3D | F_CUBE | F_MS);
return info;
}
case DXGI_FORMAT_BC1_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_BC1_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC1_UNORM_SRGB:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC2_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_BC2_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC2_UNORM_SRGB:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC3_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_BC3_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC3_UNORM_SRGB:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC4_SNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC4_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_BC4_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC5_SNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC5_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_BC5_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC6H_SF16:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC6H_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_BC6H_UF16:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC7_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_BC7_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_BC7_UNORM_SRGB:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_D16_UNORM:
{
- static const DXGISupport info(F_2D | F_CUBE | F_DS, F_3D | F_RT | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_CUBE | F_DS, F_3D | F_MIPGEN | F_RT | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_D24_UNORM_S8_UINT:
@@ -1416,397 +2013,990 @@ const DXGISupport &GetDXGISupport_11_0(DXGI_FORMAT dxgiFormat)
}
case DXGI_FORMAT_D32_FLOAT:
{
- static const DXGISupport info(F_2D | F_CUBE | F_DS, F_3D | F_RT | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_CUBE | F_DS, F_3D | F_MIPGEN | F_RT | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_D32_FLOAT_S8X24_UINT:
{
+ static const DXGISupport info(F_2D | F_CUBE | F_DS, F_3D | F_MIPGEN | F_RT | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_G8R8_G8B8_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_IA44:
+ {
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_NV11:
+ {
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_NV12:
+ {
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_P010:
+ {
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_P016:
+ {
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_P8:
+ {
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R10G10B10A2_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R10G10B10A2_UINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R10G10B10A2_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM:
+ {
+ static const DXGISupport info(0, F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, F_2D | F_3D);
+ return info;
+ }
+ case DXGI_FORMAT_R11G11B10_FLOAT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16G16B16A16_FLOAT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16G16B16A16_SINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16G16B16A16_SNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16G16B16A16_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R16G16B16A16_UINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16G16B16A16_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16G16_FLOAT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16G16_SINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16G16_SNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16G16_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R16G16_UINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16G16_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16_FLOAT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16_SINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16_SNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R16_UINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R16_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R1_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R24G8_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R24_UNORM_X8_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_CUBE | F_SAMPLE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R32G32B32A32_FLOAT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R32G32B32A32_SINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R32G32B32A32_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R32G32B32A32_UINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R32G32B32_FLOAT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN, F_MS | F_RT);
+ return info;
+ }
+ case DXGI_FORMAT_R32G32B32_SINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_SAMPLE, F_MS | F_RT);
+ return info;
+ }
+ case DXGI_FORMAT_R32G32B32_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R32G32B32_UINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_SAMPLE, F_MS | F_RT);
+ return info;
+ }
+ case DXGI_FORMAT_R32G32_FLOAT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R32G32_SINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R32G32_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R32G32_UINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R32G8X24_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R32_FLOAT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_CUBE | F_SAMPLE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R32_SINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R32_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R32_UINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R8G8B8A8_SINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R8G8B8A8_SNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R8G8B8A8_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R8G8B8A8_UINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R8G8B8A8_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R8G8_B8G8_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R8G8_SINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R8G8_SNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R8G8_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R8G8_UINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R8G8_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R8_SINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R8_SNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R8_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_R8_UINT:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R8_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_R9G9B9E5_SHAREDEXP:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_UNKNOWN:
+ {
+ static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_X24_TYPELESS_G8_UINT:
+ {
+ static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_X32_TYPELESS_G8X24_UINT:
+ {
+ static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_Y210:
+ {
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_Y216:
+ {
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_Y410:
+ {
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_Y416:
+ {
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_YUY2:
+ {
+ static const DXGISupport info(0, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+
+ default:
+ UNREACHABLE();
+ return GetDefaultSupport();
+ }
+ // clang-format on
+}
+
+const DXGISupport &GetDXGISupport_11_1(DXGI_FORMAT dxgiFormat)
+{
+ // clang-format off
+ switch (dxgiFormat)
+ {
+ case DXGI_FORMAT_420_OPAQUE:
+ {
+ static const DXGISupport info(F_2D, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_A8P8:
+ {
+ static const DXGISupport info(F_2D, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_A8_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_AI44:
+ {
+ static const DXGISupport info(F_2D, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_AYUV:
+ {
+ static const DXGISupport info(F_2D | F_RT | F_SAMPLE, F_3D | F_CUBE | F_DS | F_MIPGEN, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_B4G4R4A4_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_SAMPLE, F_DS, F_MS | F_RT);
+ return info;
+ }
+ case DXGI_FORMAT_B5G5R5A1_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_SAMPLE, F_DS, F_MS | F_RT);
+ return info;
+ }
+ case DXGI_FORMAT_B5G6R5_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_B8G8R8A8_TYPELESS:
+ {
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, F_2D | F_3D | F_CUBE);
+ return info;
+ }
+ case DXGI_FORMAT_B8G8R8A8_UNORM:
+ {
+ static const DXGISupport info(F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_2D | F_3D | F_CUBE | F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB:
+ {
+ static const DXGISupport info(F_RT | F_SAMPLE, F_DS | F_MIPGEN, F_2D | F_3D | F_CUBE | F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_B8G8R8X8_TYPELESS:
+ {
+ static const DXGISupport info(0, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, F_2D | F_3D | F_CUBE);
+ return info;
+ }
+ case DXGI_FORMAT_B8G8R8X8_UNORM:
+ {
+ static const DXGISupport info(F_RT | F_SAMPLE, F_DS | F_MIPGEN, F_2D | F_3D | F_CUBE | F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB:
+ {
+ static const DXGISupport info(F_RT | F_SAMPLE, F_DS | F_MIPGEN, F_2D | F_3D | F_CUBE | F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_BC1_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC1_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC1_UNORM_SRGB:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC2_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC2_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC2_UNORM_SRGB:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC3_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC3_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC3_UNORM_SRGB:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC4_SNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC4_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC4_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC5_SNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC5_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC5_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC6H_SF16:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC6H_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC6H_UF16:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC7_TYPELESS:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC7_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_BC7_UNORM_SRGB:
+ {
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
+ return info;
+ }
+ case DXGI_FORMAT_D16_UNORM:
+ {
+ static const DXGISupport info(F_2D | F_CUBE | F_DS, F_3D | F_MIPGEN | F_RT | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_D24_UNORM_S8_UINT:
+ {
static const DXGISupport info(F_2D | F_CUBE | F_DS, F_3D | F_RT | F_SAMPLE, F_MS);
return info;
}
+ case DXGI_FORMAT_D32_FLOAT:
+ {
+ static const DXGISupport info(F_2D | F_CUBE | F_DS, F_3D | F_MIPGEN | F_RT | F_SAMPLE, F_MS);
+ return info;
+ }
+ case DXGI_FORMAT_D32_FLOAT_S8X24_UINT:
+ {
+ static const DXGISupport info(F_2D | F_CUBE | F_DS, F_3D | F_MIPGEN | F_RT | F_SAMPLE, F_MS);
+ return info;
+ }
case DXGI_FORMAT_G8R8_G8B8_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_IA44:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_NV11:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_RT | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_RT | F_SAMPLE, F_3D | F_CUBE | F_DS | F_MIPGEN, F_MS);
return info;
}
case DXGI_FORMAT_NV12:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_RT | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_RT | F_SAMPLE, F_3D | F_CUBE | F_DS | F_MIPGEN, F_MS);
return info;
}
case DXGI_FORMAT_P010:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_RT | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_RT | F_SAMPLE, F_3D | F_CUBE | F_DS | F_MIPGEN, F_MS);
return info;
}
case DXGI_FORMAT_P016:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_RT | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_RT | F_SAMPLE, F_3D | F_CUBE | F_DS | F_MIPGEN, F_MS);
return info;
}
case DXGI_FORMAT_P8:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R10G10B10A2_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R10G10B10A2_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R10G10B10A2_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM:
{
- static const DXGISupport info(0, F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, F_2D | F_3D);
+ static const DXGISupport info(0, F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, F_2D | F_3D);
return info;
}
case DXGI_FORMAT_R11G11B10_FLOAT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R16G16B16A16_FLOAT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R16G16B16A16_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R16G16B16A16_SNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R16G16B16A16_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R16G16B16A16_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R16G16B16A16_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R16G16_FLOAT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R16G16_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R16G16_SNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R16G16_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R16G16_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R16G16_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R16_FLOAT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R16_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R16_SNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R16_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R16_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R16_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R1_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R24G8_TYPELESS:
{
- static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R24_UNORM_X8_TYPELESS:
{
- static const DXGISupport info(F_2D | F_CUBE | F_SAMPLE, F_3D | F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_CUBE | F_SAMPLE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_R32G32B32A32_FLOAT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R32G32B32A32_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R32G32B32A32_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R32G32B32A32_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R32G32B32_FLOAT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS, F_MS | F_RT);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN, F_MS | F_RT);
return info;
}
case DXGI_FORMAT_R32G32B32_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_SAMPLE, F_MS | F_RT);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_SAMPLE, F_MS | F_RT);
return info;
}
case DXGI_FORMAT_R32G32B32_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R32G32B32_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_SAMPLE, F_MS | F_RT);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_SAMPLE, F_MS | F_RT);
return info;
}
case DXGI_FORMAT_R32G32_FLOAT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R32G32_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R32G32_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R32G32_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R32G8X24_TYPELESS:
{
- static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R32_FLOAT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS:
{
- static const DXGISupport info(F_2D | F_CUBE | F_SAMPLE, F_3D | F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_CUBE | F_SAMPLE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_R32_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R32_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R32_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R8G8B8A8_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R8G8B8A8_SNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R8G8B8A8_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R8G8B8A8_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R8G8B8A8_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R8G8_B8G8_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_R8G8_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R8G8_SNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R8G8_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R8G8_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R8G8_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R8_SINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R8_SNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R8_TYPELESS:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE, F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_R8_UINT:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_SAMPLE, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT, F_DS | F_MIPGEN | F_SAMPLE, F_MS);
return info;
}
case DXGI_FORMAT_R8_UNORM:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_RT | F_SAMPLE, F_DS, F_MS);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_MIPGEN | F_RT | F_SAMPLE, F_DS, F_MS);
return info;
}
case DXGI_FORMAT_R9G9B9E5_SHAREDEXP:
{
- static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MS | F_RT, 0);
+ static const DXGISupport info(F_2D | F_3D | F_CUBE | F_SAMPLE, F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_UNKNOWN:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_X24_TYPELESS_G8_UINT:
{
- static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_X32_TYPELESS_G8X24_UINT:
{
- static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_CUBE, F_3D | F_DS | F_MIPGEN | F_MS | F_RT | F_SAMPLE, 0);
return info;
}
case DXGI_FORMAT_Y210:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_SAMPLE, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_Y216:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_SAMPLE, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_Y410:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_SAMPLE, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_Y416:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_SAMPLE, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
case DXGI_FORMAT_YUY2:
{
- static const DXGISupport info(0, F_2D | F_3D | F_CUBE | F_DS | F_MS | F_RT | F_SAMPLE, 0);
+ static const DXGISupport info(F_2D | F_SAMPLE, F_3D | F_CUBE | F_DS | F_MIPGEN | F_MS | F_RT, 0);
return info;
}
@@ -1814,6 +3004,7 @@ const DXGISupport &GetDXGISupport_11_0(DXGI_FORMAT dxgiFormat)
UNREACHABLE();
return GetDefaultSupport();
}
+ // clang-format on
}
}
@@ -1825,17 +3016,22 @@ const DXGISupport &GetDXGISupport_11_0(DXGI_FORMAT dxgiFormat)
#undef F_RT
#undef F_MS
#undef F_DS
+#undef F_MIPGEN
const DXGISupport &GetDXGISupport(DXGI_FORMAT dxgiFormat, D3D_FEATURE_LEVEL featureLevel)
{
switch (featureLevel)
{
+ case D3D_FEATURE_LEVEL_9_3:
+ return GetDXGISupport_9_3(dxgiFormat);
case D3D_FEATURE_LEVEL_10_0:
return GetDXGISupport_10_0(dxgiFormat);
case D3D_FEATURE_LEVEL_10_1:
return GetDXGISupport_10_1(dxgiFormat);
case D3D_FEATURE_LEVEL_11_0:
return GetDXGISupport_11_0(dxgiFormat);
+ case D3D_FEATURE_LEVEL_11_1:
+ return GetDXGISupport_11_1(dxgiFormat);
default:
return GetDefaultSupport();
}
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/dxgi_support_table.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/dxgi_support_table.h
index 1d8d68565e..a818f376ef 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/dxgi_support_table.h
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/dxgi_support_table.h
@@ -8,6 +8,9 @@
// version, D3D feature level, and is sometimes guaranteed or optional.
//
+#ifndef LIBANGLE_RENDERER_D3D_D3D11_DXGI_SUPPORT_TABLE_H_
+#define LIBANGLE_RENDERER_D3D_D3D11_DXGI_SUPPORT_TABLE_H_
+
#include "common/platform.h"
namespace rx
@@ -42,3 +45,5 @@ const DXGISupport &GetDXGISupport(DXGI_FORMAT dxgiFormat, D3D_FEATURE_LEVEL feat
} // namespace d3d11
} // namespace rx
+
+#endif // LIBANGLE_RENDERER_D3D_D3D11_DXGI_SUPPORT_TABLE_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/formatutils11.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/formatutils11.cpp
index f073e9f46f..ce4edd26db 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/formatutils11.cpp
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/formatutils11.cpp
@@ -9,14 +9,15 @@
#include "libANGLE/renderer/d3d/d3d11/formatutils11.h"
+#include "image_util/copyimage.h"
+#include "image_util/generatemip.h"
+#include "image_util/loadimage.h"
+
#include "libANGLE/formatutils.h"
-#include "libANGLE/renderer/d3d/copyimage.h"
#include "libANGLE/renderer/d3d/d3d11/copyvertex.h"
+#include "libANGLE/renderer/d3d/d3d11/dxgi_support_table.h"
#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
#include "libANGLE/renderer/d3d/d3d11/Renderer11.h"
-#include "libANGLE/renderer/d3d/generatemip.h"
-#include "libANGLE/renderer/d3d/loadimage.h"
-#include "libANGLE/renderer/Renderer.h"
namespace rx
{
@@ -24,559 +25,388 @@ namespace rx
namespace d3d11
{
-typedef std::map<DXGI_FORMAT, GLenum> DXGIToESFormatMap;
-
-inline void AddDXGIToESEntry(DXGIToESFormatMap *map, DXGI_FORMAT key, GLenum value)
+bool SupportsMipGen(DXGI_FORMAT dxgiFormat, D3D_FEATURE_LEVEL featureLevel)
{
- map->insert(std::make_pair(key, value));
+ const auto &support = GetDXGISupport(dxgiFormat, featureLevel);
+ ASSERT((support.optionallySupportedFlags & D3D11_FORMAT_SUPPORT_MIP_AUTOGEN) == 0);
+ return ((support.alwaysSupportedFlags & D3D11_FORMAT_SUPPORT_MIP_AUTOGEN) != 0);
}
-static DXGIToESFormatMap BuildDXGIToESFormatMap()
+DXGIFormatSize::DXGIFormatSize(GLuint pixelBits, GLuint blockWidth, GLuint blockHeight)
+ : pixelBytes(pixelBits / 8), blockWidth(blockWidth), blockHeight(blockHeight)
{
- DXGIToESFormatMap map;
-
- AddDXGIToESEntry(&map, DXGI_FORMAT_UNKNOWN, GL_NONE);
-
- AddDXGIToESEntry(&map, DXGI_FORMAT_A8_UNORM, GL_ALPHA8_EXT);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R8_UNORM, GL_R8);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R8G8_UNORM, GL_RG8);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R8G8B8A8_UNORM, GL_RGBA8);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R8G8B8A8_UNORM_SRGB, GL_SRGB8_ALPHA8);
- AddDXGIToESEntry(&map, DXGI_FORMAT_B8G8R8A8_UNORM, GL_BGRA8_EXT);
-
- AddDXGIToESEntry(&map, DXGI_FORMAT_R8_SNORM, GL_R8_SNORM);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R8G8_SNORM, GL_RG8_SNORM);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R8G8B8A8_SNORM, GL_RGBA8_SNORM);
-
- AddDXGIToESEntry(&map, DXGI_FORMAT_R8_UINT, GL_R8UI);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R16_UINT, GL_R16UI);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R32_UINT, GL_R32UI);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R8G8_UINT, GL_RG8UI);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R16G16_UINT, GL_RG16UI);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R32G32_UINT, GL_RG32UI);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R32G32B32_UINT, GL_RGB32UI);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R8G8B8A8_UINT, GL_RGBA8UI);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R16G16B16A16_UINT, GL_RGBA16UI);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R32G32B32A32_UINT, GL_RGBA32UI);
-
- AddDXGIToESEntry(&map, DXGI_FORMAT_R8_SINT, GL_R8I);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R16_SINT, GL_R16I);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R32_SINT, GL_R32I);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R8G8_SINT, GL_RG8I);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R16G16_SINT, GL_RG16I);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R32G32_SINT, GL_RG32I);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R32G32B32_SINT, GL_RGB32I);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R8G8B8A8_SINT, GL_RGBA8I);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R16G16B16A16_SINT, GL_RGBA16I);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R32G32B32A32_SINT, GL_RGBA32I);
-
- AddDXGIToESEntry(&map, DXGI_FORMAT_R10G10B10A2_UNORM, GL_RGB10_A2);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R10G10B10A2_UINT, GL_RGB10_A2UI);
-
- AddDXGIToESEntry(&map, DXGI_FORMAT_R16_FLOAT, GL_R16F);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R16G16_FLOAT, GL_RG16F);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R16G16B16A16_FLOAT, GL_RGBA16F);
-
- AddDXGIToESEntry(&map, DXGI_FORMAT_R32_FLOAT, GL_R32F);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R32G32_FLOAT, GL_RG32F);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R32G32B32_FLOAT, GL_RGB32F);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R32G32B32A32_FLOAT, GL_RGBA32F);
-
- AddDXGIToESEntry(&map, DXGI_FORMAT_R9G9B9E5_SHAREDEXP, GL_RGB9_E5);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R11G11B10_FLOAT, GL_R11F_G11F_B10F);
-
- AddDXGIToESEntry(&map, DXGI_FORMAT_R16_TYPELESS, GL_DEPTH_COMPONENT16);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R16_UNORM, GL_DEPTH_COMPONENT16);
- AddDXGIToESEntry(&map, DXGI_FORMAT_D16_UNORM, GL_DEPTH_COMPONENT16);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R24G8_TYPELESS, GL_DEPTH24_STENCIL8_OES);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R24_UNORM_X8_TYPELESS, GL_DEPTH24_STENCIL8_OES);
- AddDXGIToESEntry(&map, DXGI_FORMAT_D24_UNORM_S8_UINT, GL_DEPTH24_STENCIL8_OES);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R32G8X24_TYPELESS, GL_DEPTH32F_STENCIL8);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS, GL_DEPTH32F_STENCIL8);
- AddDXGIToESEntry(&map, DXGI_FORMAT_D32_FLOAT_S8X24_UINT, GL_DEPTH32F_STENCIL8);
- AddDXGIToESEntry(&map, DXGI_FORMAT_R32_TYPELESS, GL_DEPTH_COMPONENT32F);
- AddDXGIToESEntry(&map, DXGI_FORMAT_D32_FLOAT, GL_DEPTH_COMPONENT32F);
-
- AddDXGIToESEntry(&map, DXGI_FORMAT_BC1_UNORM, GL_COMPRESSED_RGBA_S3TC_DXT1_EXT);
- AddDXGIToESEntry(&map, DXGI_FORMAT_BC2_UNORM, GL_COMPRESSED_RGBA_S3TC_DXT3_ANGLE);
- AddDXGIToESEntry(&map, DXGI_FORMAT_BC3_UNORM, GL_COMPRESSED_RGBA_S3TC_DXT5_ANGLE);
-
- AddDXGIToESEntry(&map, DXGI_FORMAT_B5G6R5_UNORM, GL_RGB565);
- AddDXGIToESEntry(&map, DXGI_FORMAT_B5G5R5A1_UNORM, GL_RGB5_A1);
- AddDXGIToESEntry(&map, DXGI_FORMAT_B4G4R4A4_UNORM, GL_RGBA4);
-
- return map;
}
-struct D3D11FastCopyFormat
+const DXGIFormatSize &GetDXGIFormatSizeInfo(DXGI_FORMAT format)
{
- GLenum destFormat;
- GLenum destType;
- ColorCopyFunction copyFunction;
-
- D3D11FastCopyFormat(GLenum destFormat, GLenum destType, ColorCopyFunction copyFunction)
- : destFormat(destFormat), destType(destType), copyFunction(copyFunction)
- { }
-
- bool operator<(const D3D11FastCopyFormat& other) const
+ static const DXGIFormatSize sizeUnknown(0, 0, 0);
+ static const DXGIFormatSize size128(128, 1, 1);
+ static const DXGIFormatSize size96(96, 1, 1);
+ static const DXGIFormatSize size64(64, 1, 1);
+ static const DXGIFormatSize size32(32, 1, 1);
+ static const DXGIFormatSize size16(16, 1, 1);
+ static const DXGIFormatSize size8(8, 1, 1);
+ static const DXGIFormatSize sizeBC1(64, 4, 4);
+ static const DXGIFormatSize sizeBC2(128, 4, 4);
+ static const DXGIFormatSize sizeBC3(128, 4, 4);
+ static const DXGIFormatSize sizeBC4(64, 4, 4);
+ static const DXGIFormatSize sizeBC5(128, 4, 4);
+ static const DXGIFormatSize sizeBC6H(128, 4, 4);
+ static const DXGIFormatSize sizeBC7(128, 4, 4);
+ switch (format)
{
- return memcmp(this, &other, sizeof(D3D11FastCopyFormat)) < 0;
+ case DXGI_FORMAT_UNKNOWN:
+ return sizeUnknown;
+ case DXGI_FORMAT_R32G32B32A32_TYPELESS:
+ case DXGI_FORMAT_R32G32B32A32_FLOAT:
+ case DXGI_FORMAT_R32G32B32A32_UINT:
+ case DXGI_FORMAT_R32G32B32A32_SINT:
+ return size128;
+ case DXGI_FORMAT_R32G32B32_TYPELESS:
+ case DXGI_FORMAT_R32G32B32_FLOAT:
+ case DXGI_FORMAT_R32G32B32_UINT:
+ case DXGI_FORMAT_R32G32B32_SINT:
+ return size96;
+ case DXGI_FORMAT_R16G16B16A16_TYPELESS:
+ case DXGI_FORMAT_R16G16B16A16_FLOAT:
+ case DXGI_FORMAT_R16G16B16A16_UNORM:
+ case DXGI_FORMAT_R16G16B16A16_UINT:
+ case DXGI_FORMAT_R16G16B16A16_SNORM:
+ case DXGI_FORMAT_R16G16B16A16_SINT:
+ case DXGI_FORMAT_R32G32_TYPELESS:
+ case DXGI_FORMAT_R32G32_FLOAT:
+ case DXGI_FORMAT_R32G32_UINT:
+ case DXGI_FORMAT_R32G32_SINT:
+ case DXGI_FORMAT_R32G8X24_TYPELESS:
+ case DXGI_FORMAT_D32_FLOAT_S8X24_UINT:
+ case DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS:
+ case DXGI_FORMAT_X32_TYPELESS_G8X24_UINT:
+ return size64;
+ case DXGI_FORMAT_R10G10B10A2_TYPELESS:
+ case DXGI_FORMAT_R10G10B10A2_UNORM:
+ case DXGI_FORMAT_R10G10B10A2_UINT:
+ case DXGI_FORMAT_R11G11B10_FLOAT:
+ case DXGI_FORMAT_R8G8B8A8_TYPELESS:
+ case DXGI_FORMAT_R8G8B8A8_UNORM:
+ case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB:
+ case DXGI_FORMAT_R8G8B8A8_UINT:
+ case DXGI_FORMAT_R8G8B8A8_SNORM:
+ case DXGI_FORMAT_R8G8B8A8_SINT:
+ case DXGI_FORMAT_R16G16_TYPELESS:
+ case DXGI_FORMAT_R16G16_FLOAT:
+ case DXGI_FORMAT_R16G16_UNORM:
+ case DXGI_FORMAT_R16G16_UINT:
+ case DXGI_FORMAT_R16G16_SNORM:
+ case DXGI_FORMAT_R16G16_SINT:
+ case DXGI_FORMAT_R32_TYPELESS:
+ case DXGI_FORMAT_D32_FLOAT:
+ case DXGI_FORMAT_R32_FLOAT:
+ case DXGI_FORMAT_R32_UINT:
+ case DXGI_FORMAT_R32_SINT:
+ case DXGI_FORMAT_R24G8_TYPELESS:
+ case DXGI_FORMAT_D24_UNORM_S8_UINT:
+ case DXGI_FORMAT_R24_UNORM_X8_TYPELESS:
+ case DXGI_FORMAT_X24_TYPELESS_G8_UINT:
+ return size32;
+ case DXGI_FORMAT_R8G8_TYPELESS:
+ case DXGI_FORMAT_R8G8_UNORM:
+ case DXGI_FORMAT_R8G8_UINT:
+ case DXGI_FORMAT_R8G8_SNORM:
+ case DXGI_FORMAT_R8G8_SINT:
+ case DXGI_FORMAT_R16_TYPELESS:
+ case DXGI_FORMAT_R16_FLOAT:
+ case DXGI_FORMAT_D16_UNORM:
+ case DXGI_FORMAT_R16_UNORM:
+ case DXGI_FORMAT_R16_UINT:
+ case DXGI_FORMAT_R16_SNORM:
+ case DXGI_FORMAT_R16_SINT:
+ return size16;
+ case DXGI_FORMAT_R8_TYPELESS:
+ case DXGI_FORMAT_R8_UNORM:
+ case DXGI_FORMAT_R8_UINT:
+ case DXGI_FORMAT_R8_SNORM:
+ case DXGI_FORMAT_R8_SINT:
+ case DXGI_FORMAT_A8_UNORM:
+ return size8;
+ case DXGI_FORMAT_R1_UNORM:
+ UNREACHABLE();
+ return sizeUnknown;
+ case DXGI_FORMAT_R9G9B9E5_SHAREDEXP:
+ case DXGI_FORMAT_R8G8_B8G8_UNORM:
+ case DXGI_FORMAT_G8R8_G8B8_UNORM:
+ return size32;
+ case DXGI_FORMAT_BC1_TYPELESS:
+ case DXGI_FORMAT_BC1_UNORM:
+ case DXGI_FORMAT_BC1_UNORM_SRGB:
+ return sizeBC1;
+ case DXGI_FORMAT_BC2_TYPELESS:
+ case DXGI_FORMAT_BC2_UNORM:
+ case DXGI_FORMAT_BC2_UNORM_SRGB:
+ return sizeBC2;
+ case DXGI_FORMAT_BC3_TYPELESS:
+ case DXGI_FORMAT_BC3_UNORM:
+ case DXGI_FORMAT_BC3_UNORM_SRGB:
+ return sizeBC3;
+ case DXGI_FORMAT_BC4_TYPELESS:
+ case DXGI_FORMAT_BC4_UNORM:
+ case DXGI_FORMAT_BC4_SNORM:
+ return sizeBC4;
+ case DXGI_FORMAT_BC5_TYPELESS:
+ case DXGI_FORMAT_BC5_UNORM:
+ case DXGI_FORMAT_BC5_SNORM:
+ return sizeBC5;
+ case DXGI_FORMAT_B5G6R5_UNORM:
+ case DXGI_FORMAT_B5G5R5A1_UNORM:
+ return size16;
+ case DXGI_FORMAT_B8G8R8A8_UNORM:
+ case DXGI_FORMAT_B8G8R8X8_UNORM:
+ case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM:
+ case DXGI_FORMAT_B8G8R8A8_TYPELESS:
+ case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB:
+ case DXGI_FORMAT_B8G8R8X8_TYPELESS:
+ case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB:
+ return size32;
+ case DXGI_FORMAT_BC6H_TYPELESS:
+ case DXGI_FORMAT_BC6H_UF16:
+ case DXGI_FORMAT_BC6H_SF16:
+ return sizeBC6H;
+ case DXGI_FORMAT_BC7_TYPELESS:
+ case DXGI_FORMAT_BC7_UNORM:
+ case DXGI_FORMAT_BC7_UNORM_SRGB:
+ return sizeBC7;
+ case DXGI_FORMAT_AYUV:
+ case DXGI_FORMAT_Y410:
+ case DXGI_FORMAT_Y416:
+ case DXGI_FORMAT_NV12:
+ case DXGI_FORMAT_P010:
+ case DXGI_FORMAT_P016:
+ case DXGI_FORMAT_420_OPAQUE:
+ case DXGI_FORMAT_YUY2:
+ case DXGI_FORMAT_Y210:
+ case DXGI_FORMAT_Y216:
+ case DXGI_FORMAT_NV11:
+ case DXGI_FORMAT_AI44:
+ case DXGI_FORMAT_IA44:
+ case DXGI_FORMAT_P8:
+ case DXGI_FORMAT_A8P8:
+ UNREACHABLE();
+ return sizeUnknown;
+ case DXGI_FORMAT_B4G4R4A4_UNORM:
+ return size16;
+ default:
+ UNREACHABLE();
+ return sizeUnknown;
}
-};
-
-typedef std::multimap<DXGI_FORMAT, D3D11FastCopyFormat> D3D11FastCopyMap;
-
-static D3D11FastCopyMap BuildFastCopyMap()
-{
- D3D11FastCopyMap map;
-
- map.insert(std::make_pair(DXGI_FORMAT_B8G8R8A8_UNORM, D3D11FastCopyFormat(GL_RGBA, GL_UNSIGNED_BYTE, CopyBGRA8ToRGBA8)));
-
- return map;
-}
-
-struct DXGIColorFormatInfo
-{
- size_t redBits;
- size_t greenBits;
- size_t blueBits;
-
- size_t luminanceBits;
-
- size_t alphaBits;
- size_t sharedBits;
-};
-
-typedef std::map<DXGI_FORMAT, DXGIColorFormatInfo> ColorFormatInfoMap;
-typedef std::pair<DXGI_FORMAT, DXGIColorFormatInfo> ColorFormatInfoPair;
-
-static inline void InsertDXGIColorFormatInfo(ColorFormatInfoMap *map, DXGI_FORMAT format, size_t redBits, size_t greenBits,
- size_t blueBits, size_t alphaBits, size_t sharedBits)
-{
- DXGIColorFormatInfo info;
- info.redBits = redBits;
- info.greenBits = greenBits;
- info.blueBits = blueBits;
- info.alphaBits = alphaBits;
- info.sharedBits = sharedBits;
-
- map->insert(std::make_pair(format, info));
-}
-
-static ColorFormatInfoMap BuildColorFormatInfoMap()
-{
- ColorFormatInfoMap map;
-
- // | DXGI format | R | G | B | A | S |
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_A8_UNORM, 0, 0, 0, 8, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R8_UNORM, 8, 0, 0, 0, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R8G8_UNORM, 8, 8, 0, 0, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R8G8B8A8_UNORM, 8, 8, 8, 8, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R8G8B8A8_UNORM_SRGB, 8, 8, 8, 8, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_B8G8R8A8_UNORM, 8, 8, 8, 8, 0);
-
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R8_SNORM, 8, 0, 0, 0, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R8G8_SNORM, 8, 8, 0, 0, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R8G8B8A8_SNORM, 8, 8, 8, 8, 0);
-
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R8_UINT, 8, 0, 0, 0, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R16_UINT, 16, 0, 0, 0, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R32_UINT, 32, 0, 0, 0, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R8G8_UINT, 8, 8, 0, 0, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R16G16_UINT, 16, 16, 0, 0, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R32G32_UINT, 32, 32, 0, 0, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R32G32B32_UINT, 32, 32, 32, 0, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R8G8B8A8_UINT, 8, 8, 8, 8, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R16G16B16A16_UINT, 16, 16, 16, 16, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R32G32B32A32_UINT, 32, 32, 32, 32, 0);
-
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R8_SINT, 8, 0, 0, 0, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R16_SINT, 16, 0, 0, 0, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R32_SINT, 32, 0, 0, 0, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R8G8_SINT, 8, 8, 0, 0, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R16G16_SINT, 16, 16, 0, 0, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R32G32_SINT, 32, 32, 0, 0, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R32G32B32_SINT, 32, 32, 32, 0, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R8G8B8A8_SINT, 8, 8, 8, 8, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R16G16B16A16_SINT, 16, 16, 16, 16, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R32G32B32A32_SINT, 32, 32, 32, 32, 0);
-
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R10G10B10A2_UNORM, 10, 10, 10, 2, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R10G10B10A2_UINT, 10, 10, 10, 2, 0);
-
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R16_FLOAT, 16, 0, 0, 0, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R16G16_FLOAT, 16, 16, 0, 0, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R16G16B16A16_FLOAT, 16, 16, 16, 16, 0);
-
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R32_FLOAT, 32, 0, 0, 0, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R32G32_FLOAT, 32, 32, 0, 0, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R32G32B32_FLOAT, 32, 32, 32, 0, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R32G32B32A32_FLOAT, 32, 32, 32, 32, 0);
-
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R9G9B9E5_SHAREDEXP, 9, 9, 9, 0, 5);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_R11G11B10_FLOAT, 11, 11, 10, 0, 0);
-
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_B5G6R5_UNORM, 5, 6, 5, 0, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_B4G4R4A4_UNORM, 4, 4, 4, 4, 0);
- InsertDXGIColorFormatInfo(&map, DXGI_FORMAT_B5G5R5A1_UNORM, 5, 5, 5, 1, 0);
-
- return map;
-}
-
-struct DXGIDepthStencilInfo
-{
- unsigned int depthBits;
- unsigned int depthOffset;
- unsigned int stencilBits;
- unsigned int stencilOffset;
-};
-
-typedef std::map<DXGI_FORMAT, DXGIDepthStencilInfo> DepthStencilInfoMap;
-typedef std::pair<DXGI_FORMAT, DXGIDepthStencilInfo> DepthStencilInfoPair;
-
-static inline void InsertDXGIDepthStencilInfo(DepthStencilInfoMap *map, DXGI_FORMAT format, unsigned int depthBits,
- unsigned int depthOffset, unsigned int stencilBits, unsigned int stencilOffset)
-{
- DXGIDepthStencilInfo info;
- info.depthBits = depthBits;
- info.depthOffset = depthOffset;
- info.stencilBits = stencilBits;
- info.stencilOffset = stencilOffset;
-
- map->insert(std::make_pair(format, info));
}
-static DepthStencilInfoMap BuildDepthStencilInfoMap()
+constexpr VertexFormat::VertexFormat()
+ : conversionType(VERTEX_CONVERT_NONE), nativeFormat(DXGI_FORMAT_UNKNOWN), copyFunction(nullptr)
{
- DepthStencilInfoMap map;
-
- InsertDXGIDepthStencilInfo(&map, DXGI_FORMAT_R16_TYPELESS, 16, 0, 0, 0);
- InsertDXGIDepthStencilInfo(&map, DXGI_FORMAT_R16_UNORM, 16, 0, 0, 0);
- InsertDXGIDepthStencilInfo(&map, DXGI_FORMAT_D16_UNORM, 16, 0, 0, 0);
-
- InsertDXGIDepthStencilInfo(&map, DXGI_FORMAT_R24G8_TYPELESS, 24, 0, 8, 24);
- InsertDXGIDepthStencilInfo(&map, DXGI_FORMAT_R24_UNORM_X8_TYPELESS, 24, 0, 8, 24);
- InsertDXGIDepthStencilInfo(&map, DXGI_FORMAT_D24_UNORM_S8_UINT, 24, 0, 8, 24);
-
- InsertDXGIDepthStencilInfo(&map, DXGI_FORMAT_R32_TYPELESS, 32, 0, 0, 0);
- InsertDXGIDepthStencilInfo(&map, DXGI_FORMAT_R32_FLOAT, 32, 0, 0, 0);
- InsertDXGIDepthStencilInfo(&map, DXGI_FORMAT_D32_FLOAT, 32, 0, 0, 0);
-
- InsertDXGIDepthStencilInfo(&map, DXGI_FORMAT_R32G8X24_TYPELESS, 32, 0, 8, 32);
- InsertDXGIDepthStencilInfo(&map, DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS, 32, 0, 8, 32);
- InsertDXGIDepthStencilInfo(&map, DXGI_FORMAT_D32_FLOAT_S8X24_UINT, 32, 0, 8, 32);
-
- return map;
-}
-
-typedef std::map<DXGI_FORMAT, DXGIFormat> DXGIFormatInfoMap;
-
-DXGIFormat::DXGIFormat()
- : pixelBytes(0),
- blockWidth(0),
- blockHeight(0),
- redBits(0),
- greenBits(0),
- blueBits(0),
- alphaBits(0),
- sharedBits(0),
- depthBits(0),
- depthOffset(0),
- stencilBits(0),
- stencilOffset(0),
- internalFormat(GL_NONE),
- componentType(GL_NONE),
- mipGenerationFunction(NULL),
- colorReadFunction(NULL),
- fastCopyFunctions(),
- nativeMipmapSupport(NULL)
-{
-}
-
-static bool NeverSupported(D3D_FEATURE_LEVEL)
-{
- return false;
-}
-
-template <D3D_FEATURE_LEVEL requiredFeatureLevel>
-static bool RequiresFeatureLevel(D3D_FEATURE_LEVEL featureLevel)
-{
- return featureLevel >= requiredFeatureLevel;
}
-ColorCopyFunction DXGIFormat::getFastCopyFunction(GLenum format, GLenum type) const
+constexpr VertexFormat::VertexFormat(VertexConversionType conversionTypeIn,
+ DXGI_FORMAT nativeFormatIn,
+ VertexCopyFunction copyFunctionIn)
+ : conversionType(conversionTypeIn), nativeFormat(nativeFormatIn), copyFunction(copyFunctionIn)
{
- FastCopyFunctionMap::const_iterator iter = fastCopyFunctions.find(std::make_pair(format, type));
- return (iter != fastCopyFunctions.end()) ? iter->second : NULL;
}
-void AddDXGIFormat(DXGIFormatInfoMap *map, DXGI_FORMAT dxgiFormat, GLuint pixelBits, GLuint blockWidth, GLuint blockHeight,
- GLenum componentType, MipGenerationFunction mipFunc, ColorReadFunction readFunc, NativeMipmapGenerationSupportFunction nativeMipmapSupport)
+const VertexFormat *GetVertexFormatInfo_FL_9_3(gl::VertexFormatType vertexFormatType)
{
- DXGIFormat info;
- info.pixelBytes = pixelBits / 8;
- info.blockWidth = blockWidth;
- info.blockHeight = blockHeight;
-
- static const ColorFormatInfoMap colorInfoMap = BuildColorFormatInfoMap();
- ColorFormatInfoMap::const_iterator colorInfoIter = colorInfoMap.find(dxgiFormat);
- if (colorInfoIter != colorInfoMap.end())
- {
- const DXGIColorFormatInfo &colorInfo = colorInfoIter->second;
- info.redBits = static_cast<GLuint>(colorInfo.redBits);
- info.greenBits = static_cast<GLuint>(colorInfo.greenBits);
- info.blueBits = static_cast<GLuint>(colorInfo.blueBits);
- info.alphaBits = static_cast<GLuint>(colorInfo.alphaBits);
- info.sharedBits = static_cast<GLuint>(colorInfo.sharedBits);
- }
-
- static const DepthStencilInfoMap dsInfoMap = BuildDepthStencilInfoMap();
- DepthStencilInfoMap::const_iterator dsInfoIter = dsInfoMap.find(dxgiFormat);
- if (dsInfoIter != dsInfoMap.end())
- {
- const DXGIDepthStencilInfo &dsInfo = dsInfoIter->second;
- info.depthBits = dsInfo.depthBits;
- info.depthOffset = dsInfo.depthOffset;
- info.stencilBits = dsInfo.stencilBits;
- info.stencilOffset = dsInfo.stencilOffset;
- }
-
- static const DXGIToESFormatMap dxgiToESMap = BuildDXGIToESFormatMap();
- DXGIToESFormatMap::const_iterator dxgiToESIter = dxgiToESMap.find(dxgiFormat);
- info.internalFormat = (dxgiToESIter != dxgiToESMap.end()) ? dxgiToESIter->second : GL_NONE;
-
- info.componentType = componentType;
-
- info.mipGenerationFunction = mipFunc;
- info.colorReadFunction = readFunc;
+ // D3D11 Feature Level 9_3 doesn't support as many formats for vertex buffer resource as Feature
+ // Level 10_0+.
+ // http://msdn.microsoft.com/en-us/library/windows/desktop/ff471324(v=vs.85).aspx
- static const D3D11FastCopyMap fastCopyMap = BuildFastCopyMap();
- std::pair<D3D11FastCopyMap::const_iterator, D3D11FastCopyMap::const_iterator> fastCopyIter = fastCopyMap.equal_range(dxgiFormat);
- for (D3D11FastCopyMap::const_iterator i = fastCopyIter.first; i != fastCopyIter.second; i++)
+ switch (vertexFormatType)
{
- info.fastCopyFunctions.insert(std::make_pair(std::make_pair(i->second.destFormat, i->second.destType), i->second.copyFunction));
- }
-
- info.nativeMipmapSupport = nativeMipmapSupport;
-
- map->insert(std::make_pair(dxgiFormat, info));
-}
-
-// A map to determine the pixel size and mipmap generation function of a given DXGI format
-static DXGIFormatInfoMap BuildDXGIFormatInfoMap()
-{
- DXGIFormatInfoMap map;
-
- // | DXGI format |S |W |H |Component Type | Mip generation function | Color read function | Native mipmap function
- AddDXGIFormat(&map, DXGI_FORMAT_UNKNOWN, 0, 0, 0, GL_NONE, NULL, NULL, NeverSupported);
-
- AddDXGIFormat(&map, DXGI_FORMAT_A8_UNORM, 8, 1, 1, GL_UNSIGNED_NORMALIZED, GenerateMip<A8>, ReadColor<A8, GLfloat>, RequiresFeatureLevel<D3D_FEATURE_LEVEL_10_0>);
- AddDXGIFormat(&map, DXGI_FORMAT_R8_UNORM, 8, 1, 1, GL_UNSIGNED_NORMALIZED, GenerateMip<R8>, ReadColor<R8, GLfloat>, RequiresFeatureLevel<D3D_FEATURE_LEVEL_10_0>);
- AddDXGIFormat(&map, DXGI_FORMAT_R8G8_UNORM, 16, 1, 1, GL_UNSIGNED_NORMALIZED, GenerateMip<R8G8>, ReadColor<R8G8, GLfloat>, RequiresFeatureLevel<D3D_FEATURE_LEVEL_10_0>);
- AddDXGIFormat(&map, DXGI_FORMAT_R8G8B8A8_UNORM, 32, 1, 1, GL_UNSIGNED_NORMALIZED, GenerateMip<R8G8B8A8>, ReadColor<R8G8B8A8, GLfloat>, RequiresFeatureLevel<D3D_FEATURE_LEVEL_9_1>);
- AddDXGIFormat(&map, DXGI_FORMAT_R8G8B8A8_UNORM_SRGB, 32, 1, 1, GL_UNSIGNED_NORMALIZED, GenerateMip<R8G8B8A8>, ReadColor<R8G8B8A8, GLfloat>, RequiresFeatureLevel<D3D_FEATURE_LEVEL_9_1>);
- AddDXGIFormat(&map, DXGI_FORMAT_B8G8R8A8_UNORM, 32, 1, 1, GL_UNSIGNED_NORMALIZED, GenerateMip<B8G8R8A8>, ReadColor<B8G8R8A8, GLfloat>, RequiresFeatureLevel<D3D_FEATURE_LEVEL_9_1>);
-
- AddDXGIFormat(&map, DXGI_FORMAT_R8_SNORM, 8, 1, 1, GL_SIGNED_NORMALIZED, GenerateMip<R8S>, ReadColor<R8S, GLfloat> , RequiresFeatureLevel<D3D_FEATURE_LEVEL_10_0>);
- AddDXGIFormat(&map, DXGI_FORMAT_R8G8_SNORM, 16, 1, 1, GL_SIGNED_NORMALIZED, GenerateMip<R8G8S>, ReadColor<R8G8S, GLfloat> , RequiresFeatureLevel<D3D_FEATURE_LEVEL_10_0>);
- AddDXGIFormat(&map, DXGI_FORMAT_R8G8B8A8_SNORM, 32, 1, 1, GL_SIGNED_NORMALIZED, GenerateMip<R8G8B8A8S>, ReadColor<R8G8B8A8S, GLfloat>, RequiresFeatureLevel<D3D_FEATURE_LEVEL_10_0>);
-
- AddDXGIFormat(&map, DXGI_FORMAT_R8_UINT, 8, 1, 1, GL_UNSIGNED_INT, GenerateMip<R8>, ReadColor<R8, GLuint>, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R16_UINT, 16, 1, 1, GL_UNSIGNED_INT, GenerateMip<R16>, ReadColor<R16, GLuint>, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R32_UINT, 32, 1, 1, GL_UNSIGNED_INT, GenerateMip<R32>, ReadColor<R32, GLuint>, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R8G8_UINT, 16, 1, 1, GL_UNSIGNED_INT, GenerateMip<R8G8>, ReadColor<R8G8, GLuint>, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R16G16_UINT, 32, 1, 1, GL_UNSIGNED_INT, GenerateMip<R16G16>, ReadColor<R16G16, GLuint>, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R32G32_UINT, 64, 1, 1, GL_UNSIGNED_INT, GenerateMip<R32G32>, ReadColor<R32G32, GLuint>, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R32G32B32_UINT, 96, 1, 1, GL_UNSIGNED_INT, GenerateMip<R32G32B32>, ReadColor<R32G32B32, GLuint>, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R8G8B8A8_UINT, 32, 1, 1, GL_UNSIGNED_INT, GenerateMip<R8G8B8A8>, ReadColor<R8G8B8A8, GLuint>, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R16G16B16A16_UINT, 64, 1, 1, GL_UNSIGNED_INT, GenerateMip<R16G16B16A16>, ReadColor<R16G16B16A16, GLuint>, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R32G32B32A32_UINT, 128, 1, 1, GL_UNSIGNED_INT, GenerateMip<R32G32B32A32>, ReadColor<R32G32B32A32, GLuint>, NeverSupported);
+ // GL_BYTE -- unnormalized
+ case gl::VERTEX_FORMAT_SBYTE1:
+ {
+ static constexpr VertexFormat info(VERTEX_CONVERT_BOTH, DXGI_FORMAT_R16G16_SINT,
+ &Copy8SintTo16SintVertexData<1, 2>);
+ return &info;
+ }
+ case gl::VERTEX_FORMAT_SBYTE2:
+ {
+ static constexpr VertexFormat info(VERTEX_CONVERT_BOTH, DXGI_FORMAT_R16G16_SINT,
+ &Copy8SintTo16SintVertexData<2, 2>);
+ return &info;
+ }
+ case gl::VERTEX_FORMAT_SBYTE3:
+ {
+ static constexpr VertexFormat info(VERTEX_CONVERT_BOTH, DXGI_FORMAT_R16G16B16A16_SINT,
+ &Copy8SintTo16SintVertexData<3, 4>);
+ return &info;
+ }
+ case gl::VERTEX_FORMAT_SBYTE4:
+ {
+ static constexpr VertexFormat info(VERTEX_CONVERT_BOTH, DXGI_FORMAT_R16G16B16A16_SINT,
+ &Copy8SintTo16SintVertexData<4, 4>);
+ return &info;
+ }
- AddDXGIFormat(&map, DXGI_FORMAT_R8_SINT, 8, 1, 1, GL_INT, GenerateMip<R8S>, ReadColor<R8S, GLint>, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R16_SINT, 16, 1, 1, GL_INT, GenerateMip<R16S>, ReadColor<R16S, GLint>, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R32_SINT, 32, 1, 1, GL_INT, GenerateMip<R32S>, ReadColor<R32S, GLint>, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R8G8_SINT, 16, 1, 1, GL_INT, GenerateMip<R8G8S>, ReadColor<R8G8S, GLint>, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R16G16_SINT, 32, 1, 1, GL_INT, GenerateMip<R16G16S>, ReadColor<R16G16S, GLint>, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R32G32_SINT, 64, 1, 1, GL_INT, GenerateMip<R32G32S>, ReadColor<R32G32S, GLint>, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R32G32B32_SINT, 96, 1, 1, GL_INT, GenerateMip<R32G32B32S>, ReadColor<R32G32B32S, GLint>, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R8G8B8A8_SINT, 32, 1, 1, GL_INT, GenerateMip<R8G8B8A8S>, ReadColor<R8G8B8A8S, GLint>, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R16G16B16A16_SINT, 64, 1, 1, GL_INT, GenerateMip<R16G16B16A16S>, ReadColor<R16G16B16A16S, GLint>, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R32G32B32A32_SINT, 128, 1, 1, GL_INT, GenerateMip<R32G32B32A32S>, ReadColor<R32G32B32A32S, GLint>, NeverSupported);
+ // GL_BYTE -- normalized
+ case gl::VERTEX_FORMAT_SBYTE1_NORM:
+ {
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R16G16_SNORM,
+ &Copy8SnormTo16SnormVertexData<1, 2>);
+ return &info;
+ }
+ case gl::VERTEX_FORMAT_SBYTE2_NORM:
+ {
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R16G16_SNORM,
+ &Copy8SnormTo16SnormVertexData<2, 2>);
+ return &info;
+ }
+ case gl::VERTEX_FORMAT_SBYTE3_NORM:
+ {
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R16G16B16A16_SNORM,
+ &Copy8SnormTo16SnormVertexData<3, 4>);
+ return &info;
+ }
+ case gl::VERTEX_FORMAT_SBYTE4_NORM:
+ {
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R16G16B16A16_SNORM,
+ &Copy8SnormTo16SnormVertexData<4, 4>);
+ return &info;
+ }
- AddDXGIFormat(&map, DXGI_FORMAT_R10G10B10A2_UNORM, 32, 1, 1, GL_UNSIGNED_NORMALIZED, GenerateMip<R10G10B10A2>, ReadColor<R10G10B10A2, GLfloat>, RequiresFeatureLevel<D3D_FEATURE_LEVEL_10_0>);
- AddDXGIFormat(&map, DXGI_FORMAT_R10G10B10A2_UINT, 32, 1, 1, GL_UNSIGNED_INT, GenerateMip<R10G10B10A2>, ReadColor<R10G10B10A2, GLuint>, NeverSupported);
+ // GL_UNSIGNED_BYTE -- un-normalized
+ // NOTE: 3 and 4 component unnormalized GL_UNSIGNED_BYTE should use the default format
+ // table.
+ case gl::VERTEX_FORMAT_UBYTE1:
+ {
+ static constexpr VertexFormat info(VERTEX_CONVERT_BOTH, DXGI_FORMAT_R8G8B8A8_UINT,
+ &CopyNativeVertexData<GLubyte, 1, 4, 1>);
+ return &info;
+ }
+ case gl::VERTEX_FORMAT_UBYTE2:
+ {
+ static constexpr VertexFormat info(VERTEX_CONVERT_BOTH, DXGI_FORMAT_R8G8B8A8_UINT,
+ &CopyNativeVertexData<GLubyte, 2, 4, 1>);
+ return &info;
+ }
- AddDXGIFormat(&map, DXGI_FORMAT_R16_FLOAT, 16, 1, 1, GL_FLOAT, GenerateMip<R16F>, ReadColor<R16F, GLfloat>, RequiresFeatureLevel<D3D_FEATURE_LEVEL_10_0>);
- AddDXGIFormat(&map, DXGI_FORMAT_R16G16_FLOAT, 32, 1, 1, GL_FLOAT, GenerateMip<R16G16F>, ReadColor<R16G16F, GLfloat>, RequiresFeatureLevel<D3D_FEATURE_LEVEL_9_2>);
- AddDXGIFormat(&map, DXGI_FORMAT_R16G16B16A16_FLOAT, 64, 1, 1, GL_FLOAT, GenerateMip<R16G16B16A16F>, ReadColor<R16G16B16A16F, GLfloat>, RequiresFeatureLevel<D3D_FEATURE_LEVEL_9_2>);
+ // GL_UNSIGNED_BYTE -- normalized
+ // NOTE: 3 and 4 component normalized GL_UNSIGNED_BYTE should use the default format table.
- AddDXGIFormat(&map, DXGI_FORMAT_R32_FLOAT, 32, 1, 1, GL_FLOAT, GenerateMip<R32F>, ReadColor<R32F, GLfloat>, RequiresFeatureLevel<D3D_FEATURE_LEVEL_9_2>);
- AddDXGIFormat(&map, DXGI_FORMAT_R32G32_FLOAT, 64, 1, 1, GL_FLOAT, GenerateMip<R32G32F>, ReadColor<R32G32F, GLfloat>, RequiresFeatureLevel<D3D_FEATURE_LEVEL_10_0>);
- AddDXGIFormat(&map, DXGI_FORMAT_R32G32B32_FLOAT, 96, 1, 1, GL_FLOAT, NULL, NULL, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R32G32B32A32_FLOAT, 128, 1, 1, GL_FLOAT, GenerateMip<R32G32B32A32F>, ReadColor<R32G32B32A32F, GLfloat>, RequiresFeatureLevel<D3D_FEATURE_LEVEL_9_3>);
+ // GL_UNSIGNED_BYTE -- normalized
+ case gl::VERTEX_FORMAT_UBYTE1_NORM:
+ {
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R8G8B8A8_UNORM,
+ &CopyNativeVertexData<GLubyte, 1, 4, UINT8_MAX>);
+ return &info;
+ }
+ case gl::VERTEX_FORMAT_UBYTE2_NORM:
+ {
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R8G8B8A8_UNORM,
+ &CopyNativeVertexData<GLubyte, 2, 4, UINT8_MAX>);
+ return &info;
+ }
- AddDXGIFormat(&map, DXGI_FORMAT_R9G9B9E5_SHAREDEXP, 32, 1, 1, GL_FLOAT, GenerateMip<R9G9B9E5>, ReadColor<R9G9B9E5, GLfloat>, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R11G11B10_FLOAT, 32, 1, 1, GL_FLOAT, GenerateMip<R11G11B10F>, ReadColor<R11G11B10F, GLfloat>, RequiresFeatureLevel<D3D_FEATURE_LEVEL_10_0>);
+ // GL_SHORT -- un-normalized
+ // NOTE: 2, 3 and 4 component unnormalized GL_SHORT should use the default format table.
+ case gl::VERTEX_FORMAT_SSHORT1:
+ {
+ static constexpr VertexFormat info(VERTEX_CONVERT_BOTH, DXGI_FORMAT_R16G16_SINT,
+ &CopyNativeVertexData<GLshort, 1, 2, 0>);
+ return &info;
+ }
- AddDXGIFormat(&map, DXGI_FORMAT_R16_TYPELESS, 16, 1, 1, GL_NONE, NULL, NULL, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R16_UNORM, 16, 1, 1, GL_UNSIGNED_NORMALIZED, NULL, NULL, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_D16_UNORM, 16, 1, 1, GL_UNSIGNED_NORMALIZED, NULL, NULL, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R24G8_TYPELESS, 32, 1, 1, GL_NONE, NULL, NULL, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R24_UNORM_X8_TYPELESS, 32, 1, 1, GL_NONE, NULL, NULL, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_D24_UNORM_S8_UINT, 32, 1, 1, GL_UNSIGNED_INT, NULL, NULL, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R32G8X24_TYPELESS, 64, 1, 1, GL_NONE, NULL, NULL, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS, 64, 1, 1, GL_NONE, NULL, NULL, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_D32_FLOAT_S8X24_UINT, 64, 1, 1, GL_UNSIGNED_INT, NULL, NULL, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R32_TYPELESS, 32, 1, 1, GL_NONE, NULL, NULL, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_D32_FLOAT, 32, 1, 1, GL_FLOAT, NULL, NULL, NeverSupported);
+ // GL_SHORT -- normalized
+ // NOTE: 2, 3 and 4 component normalized GL_SHORT should use the default format table.
+ case gl::VERTEX_FORMAT_SSHORT1_NORM:
+ {
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R16G16_SNORM,
+ &CopyNativeVertexData<GLshort, 1, 2, 0>);
+ return &info;
+ }
- AddDXGIFormat(&map, DXGI_FORMAT_BC1_UNORM, 64, 4, 4, GL_UNSIGNED_NORMALIZED, NULL, NULL, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_BC2_UNORM, 128, 4, 4, GL_UNSIGNED_NORMALIZED, NULL, NULL, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_BC3_UNORM, 128, 4, 4, GL_UNSIGNED_NORMALIZED, NULL, NULL, NeverSupported);
+ // GL_UNSIGNED_SHORT -- un-normalized
+ case gl::VERTEX_FORMAT_USHORT1:
+ {
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32_FLOAT,
+ &CopyTo32FVertexData<GLushort, 1, 2, false>);
+ return &info;
+ }
+ case gl::VERTEX_FORMAT_USHORT2:
+ {
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32_FLOAT,
+ &CopyTo32FVertexData<GLushort, 2, 2, false>);
+ return &info;
+ }
+ case gl::VERTEX_FORMAT_USHORT3:
+ {
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32B32_FLOAT,
+ &CopyTo32FVertexData<GLushort, 3, 3, false>);
+ return &info;
+ }
+ case gl::VERTEX_FORMAT_USHORT4:
+ {
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32B32A32_FLOAT,
+ &CopyTo32FVertexData<GLushort, 4, 4, false>);
+ return &info;
+ }
- // B5G6R5 in D3D11 is treated the same as R5G6B5 in D3D9, so reuse the R5G6B5 functions used by the D3D9 renderer.
- // The same applies to B4G4R4A4 and B5G5R5A1 with A4R4G4B4 and A1R5G5B5 respectively.
- AddDXGIFormat(&map, DXGI_FORMAT_B5G6R5_UNORM, 16, 1, 1, GL_UNSIGNED_NORMALIZED, GenerateMip<R5G6B5>, ReadColor<R5G6B5, GLfloat>, RequiresFeatureLevel<D3D_FEATURE_LEVEL_9_1>);
- AddDXGIFormat(&map, DXGI_FORMAT_B4G4R4A4_UNORM, 16, 1, 1, GL_UNSIGNED_NORMALIZED, GenerateMip<A4R4G4B4>, ReadColor<A4R4G4B4, GLfloat>, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_B5G5R5A1_UNORM, 16, 1, 1, GL_UNSIGNED_NORMALIZED, GenerateMip<A1R5G5B5>, ReadColor<A1R5G5B5, GLfloat>, NeverSupported);
+ // GL_UNSIGNED_SHORT -- normalized
+ case gl::VERTEX_FORMAT_USHORT1_NORM:
+ {
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32_FLOAT,
+ &CopyTo32FVertexData<GLushort, 1, 2, true>);
+ return &info;
+ }
+ case gl::VERTEX_FORMAT_USHORT2_NORM:
+ {
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32_FLOAT,
+ &CopyTo32FVertexData<GLushort, 2, 2, true>);
+ return &info;
+ }
+ case gl::VERTEX_FORMAT_USHORT3_NORM:
+ {
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32B32_FLOAT,
+ &CopyTo32FVertexData<GLushort, 3, 3, true>);
+ return &info;
+ }
+ case gl::VERTEX_FORMAT_USHORT4_NORM:
+ {
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32B32A32_FLOAT,
+ &CopyTo32FVertexData<GLushort, 4, 4, true>);
+ return &info;
+ }
- // Useful formats for vertex buffers
- AddDXGIFormat(&map, DXGI_FORMAT_R16_UNORM, 16, 1, 1, GL_UNSIGNED_NORMALIZED, NULL, NULL, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R16_SNORM, 16, 1, 1, GL_SIGNED_NORMALIZED, NULL, NULL, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R16G16_UNORM, 32, 1, 1, GL_UNSIGNED_NORMALIZED, NULL, NULL, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R16G16_SNORM, 32, 1, 1, GL_SIGNED_NORMALIZED, NULL, NULL, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R16G16B16A16_UNORM, 64, 1, 1, GL_UNSIGNED_NORMALIZED, NULL, NULL, NeverSupported);
- AddDXGIFormat(&map, DXGI_FORMAT_R16G16B16A16_SNORM, 64, 1, 1, GL_SIGNED_NORMALIZED, NULL, NULL, NeverSupported);
+ // GL_FIXED
+ // TODO: Add test to verify that this works correctly.
+ // NOTE: 2, 3 and 4 component GL_FIXED should use the default format table.
+ case gl::VERTEX_FORMAT_FIXED1:
+ {
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32_FLOAT,
+ &Copy32FixedTo32FVertexData<1, 2>);
+ return &info;
+ }
- return map;
-}
+ // GL_FLOAT
+ // TODO: Add test to verify that this works correctly.
+ // NOTE: 2, 3 and 4 component GL_FLOAT should use the default format table.
+ case gl::VERTEX_FORMAT_FLOAT1:
+ {
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32_FLOAT,
+ &CopyNativeVertexData<GLfloat, 1, 2, 0>);
+ return &info;
+ }
-const DXGIFormat &GetDXGIFormatInfo(DXGI_FORMAT format)
-{
- static const DXGIFormatInfoMap infoMap = BuildDXGIFormatInfoMap();
- DXGIFormatInfoMap::const_iterator iter = infoMap.find(format);
- if (iter != infoMap.end())
- {
- return iter->second;
- }
- else
- {
- static DXGIFormat defaultInfo;
- return defaultInfo;
+ default:
+ return nullptr;
}
}
-typedef std::map<gl::VertexFormatType, VertexFormat> D3D11VertexFormatInfoMap;
-typedef std::pair<gl::VertexFormatType, VertexFormat> D3D11VertexFormatPair;
-
-VertexFormat::VertexFormat()
- : conversionType(VERTEX_CONVERT_NONE),
- nativeFormat(DXGI_FORMAT_UNKNOWN),
- copyFunction(NULL)
-{
-}
-
-VertexFormat::VertexFormat(VertexConversionType conversionTypeIn,
- DXGI_FORMAT nativeFormatIn,
- VertexCopyFunction copyFunctionIn)
- : conversionType(conversionTypeIn),
- nativeFormat(nativeFormatIn),
- copyFunction(copyFunctionIn)
-{
-}
-
-static void AddVertexFormatInfo(D3D11VertexFormatInfoMap *map,
- GLenum inputType,
- GLboolean normalized,
- GLuint componentCount,
- VertexConversionType conversionType,
- DXGI_FORMAT nativeFormat,
- VertexCopyFunction copyFunction)
-{
- gl::VertexFormatType formatType = gl::GetVertexFormatType(inputType, normalized, componentCount, false);
-
- VertexFormat info;
- info.conversionType = conversionType;
- info.nativeFormat = nativeFormat;
- info.copyFunction = copyFunction;
-
- map->insert(D3D11VertexFormatPair(formatType, info));
-}
-
-static D3D11VertexFormatInfoMap BuildD3D11_FL9_3VertexFormatInfoOverrideMap()
-{
- // D3D11 Feature Level 9_3 doesn't support as many formats for vertex buffer resource as Feature Level 10_0+.
- // http://msdn.microsoft.com/en-us/library/windows/desktop/ff471324(v=vs.85).aspx
-
- D3D11VertexFormatInfoMap map;
-
- // GL_BYTE -- unnormalized
- AddVertexFormatInfo(&map, GL_BYTE, GL_FALSE, 1, VERTEX_CONVERT_BOTH, DXGI_FORMAT_R16G16_SINT, &Copy8SintTo16SintVertexData<1, 2>);
- AddVertexFormatInfo(&map, GL_BYTE, GL_FALSE, 2, VERTEX_CONVERT_BOTH, DXGI_FORMAT_R16G16_SINT, &Copy8SintTo16SintVertexData<2, 2>);
- AddVertexFormatInfo(&map, GL_BYTE, GL_FALSE, 3, VERTEX_CONVERT_BOTH, DXGI_FORMAT_R16G16B16A16_SINT, &Copy8SintTo16SintVertexData<3, 4>);
- AddVertexFormatInfo(&map, GL_BYTE, GL_FALSE, 4, VERTEX_CONVERT_BOTH, DXGI_FORMAT_R16G16B16A16_SINT, &Copy8SintTo16SintVertexData<4, 4>);
-
- // GL_BYTE -- normalized
- AddVertexFormatInfo(&map, GL_BYTE, GL_TRUE, 1, VERTEX_CONVERT_CPU, DXGI_FORMAT_R16G16_SNORM, &Copy8SnormTo16SnormVertexData<1, 2>);
- AddVertexFormatInfo(&map, GL_BYTE, GL_TRUE, 2, VERTEX_CONVERT_CPU, DXGI_FORMAT_R16G16_SNORM, &Copy8SnormTo16SnormVertexData<2, 2>);
- AddVertexFormatInfo(&map, GL_BYTE, GL_TRUE, 3, VERTEX_CONVERT_CPU, DXGI_FORMAT_R16G16B16A16_SNORM, &Copy8SnormTo16SnormVertexData<3, 4>);
- AddVertexFormatInfo(&map, GL_BYTE, GL_TRUE, 4, VERTEX_CONVERT_CPU, DXGI_FORMAT_R16G16B16A16_SNORM, &Copy8SnormTo16SnormVertexData<4, 4>);
-
- // GL_UNSIGNED_BYTE -- unnormalized
- AddVertexFormatInfo(&map, GL_UNSIGNED_BYTE, GL_FALSE, 1, VERTEX_CONVERT_BOTH, DXGI_FORMAT_R8G8B8A8_UINT, &CopyNativeVertexData<GLubyte, 1, 4, 1>);
- AddVertexFormatInfo(&map, GL_UNSIGNED_BYTE, GL_FALSE, 2, VERTEX_CONVERT_BOTH, DXGI_FORMAT_R8G8B8A8_UINT, &CopyNativeVertexData<GLubyte, 2, 4, 1>);
- // NOTE: 3 and 4 component unnormalized GL_UNSIGNED_BYTE should use the default format table.
-
- // GL_UNSIGNED_BYTE -- normalized
- AddVertexFormatInfo(&map, GL_UNSIGNED_BYTE, GL_TRUE, 1, VERTEX_CONVERT_CPU, DXGI_FORMAT_R8G8B8A8_UNORM, &CopyNativeVertexData<GLubyte, 1, 4, UINT8_MAX>);
- AddVertexFormatInfo(&map, GL_UNSIGNED_BYTE, GL_TRUE, 2, VERTEX_CONVERT_CPU, DXGI_FORMAT_R8G8B8A8_UNORM, &CopyNativeVertexData<GLubyte, 2, 4, UINT8_MAX>);
- // NOTE: 3 and 4 component normalized GL_UNSIGNED_BYTE should use the default format table.
-
- // GL_SHORT -- unnormalized
- AddVertexFormatInfo(&map, GL_SHORT, GL_FALSE, 1, VERTEX_CONVERT_BOTH, DXGI_FORMAT_R16G16_SINT, &CopyNativeVertexData<GLshort, 1, 2, 0>);
- // NOTE: 2, 3 and 4 component unnormalized GL_SHORT should use the default format table.
-
- // GL_SHORT -- normalized
- AddVertexFormatInfo(&map, GL_SHORT, GL_TRUE, 1, VERTEX_CONVERT_CPU, DXGI_FORMAT_R16G16_SNORM, &CopyNativeVertexData<GLshort, 1, 2, 0>);
- // NOTE: 2, 3 and 4 component normalized GL_SHORT should use the default format table.
-
- // GL_UNSIGNED_SHORT -- unnormalized
- AddVertexFormatInfo(&map, GL_UNSIGNED_SHORT, GL_FALSE, 1, VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32_FLOAT, &CopyTo32FVertexData<GLushort, 1, 2, false>);
- AddVertexFormatInfo(&map, GL_UNSIGNED_SHORT, GL_FALSE, 2, VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32_FLOAT, &CopyTo32FVertexData<GLushort, 2, 2, false>);
- AddVertexFormatInfo(&map, GL_UNSIGNED_SHORT, GL_FALSE, 3, VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32B32_FLOAT, &CopyTo32FVertexData<GLushort, 3, 3, false>);
- AddVertexFormatInfo(&map, GL_UNSIGNED_SHORT, GL_FALSE, 4, VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32B32A32_FLOAT, &CopyTo32FVertexData<GLushort, 4, 4, false>);
-
- // GL_UNSIGNED_SHORT -- normalized
- AddVertexFormatInfo(&map, GL_UNSIGNED_SHORT, GL_TRUE, 1, VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32_FLOAT, &CopyTo32FVertexData<GLushort, 1, 2, true>);
- AddVertexFormatInfo(&map, GL_UNSIGNED_SHORT, GL_TRUE, 2, VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32_FLOAT, &CopyTo32FVertexData<GLushort, 2, 2, true>);
- AddVertexFormatInfo(&map, GL_UNSIGNED_SHORT, GL_TRUE, 3, VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32B32_FLOAT, &CopyTo32FVertexData<GLushort, 3, 3, true>);
- AddVertexFormatInfo(&map, GL_UNSIGNED_SHORT, GL_TRUE, 4, VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32B32A32_FLOAT, &CopyTo32FVertexData<GLushort, 4, 4, true>);
-
- // GL_FIXED
- // TODO: Add test to verify that this works correctly.
- AddVertexFormatInfo(&map, GL_FIXED, GL_FALSE, 1, VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32_FLOAT, &Copy32FixedTo32FVertexData<1, 2>);
- // NOTE: 2, 3 and 4 component GL_FIXED should use the default format table.
-
- // GL_FLOAT
- // TODO: Add test to verify that this works correctly.
- AddVertexFormatInfo(&map, GL_FLOAT, GL_FALSE, 1, VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32_FLOAT, &CopyNativeVertexData<GLfloat, 1, 2, 0>);
- // NOTE: 2, 3 and 4 component GL_FLOAT should use the default format table.
-
- return map;
-}
-
const VertexFormat &GetVertexFormatInfo(gl::VertexFormatType vertexFormatType, D3D_FEATURE_LEVEL featureLevel)
{
if (featureLevel == D3D_FEATURE_LEVEL_9_3)
{
- static const D3D11VertexFormatInfoMap vertexFormatMapFL9_3Override =
- BuildD3D11_FL9_3VertexFormatInfoOverrideMap();
-
- // First see if the format has a special mapping for FL9_3
- auto iter = vertexFormatMapFL9_3Override.find(vertexFormatType);
- if (iter != vertexFormatMapFL9_3Override.end())
+ const VertexFormat *result = GetVertexFormatInfo_FL_9_3(vertexFormatType);
+ if (result)
{
- return iter->second;
+ return *result;
}
}
@@ -589,354 +419,418 @@ const VertexFormat &GetVertexFormatInfo(gl::VertexFormatType vertexFormatType, D
// GL_BYTE -- un-normalized
case gl::VERTEX_FORMAT_SBYTE1:
{
- static const VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R8_SINT, &CopyNativeVertexData<GLbyte, 1, 1, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R8_SINT,
+ &CopyNativeVertexData<GLbyte, 1, 1, 0>);
return info;
}
case gl::VERTEX_FORMAT_SBYTE2:
{
- static const VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R8G8_SINT, &CopyNativeVertexData<GLbyte, 2, 2, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R8G8_SINT,
+ &CopyNativeVertexData<GLbyte, 2, 2, 0>);
return info;
}
case gl::VERTEX_FORMAT_SBYTE3:
{
- static const VertexFormat info(VERTEX_CONVERT_BOTH, DXGI_FORMAT_R8G8B8A8_SINT, &CopyNativeVertexData<GLbyte, 3, 4, 1>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_BOTH, DXGI_FORMAT_R8G8B8A8_SINT,
+ &CopyNativeVertexData<GLbyte, 3, 4, 1>);
return info;
}
case gl::VERTEX_FORMAT_SBYTE4:
{
- static const VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R8G8B8A8_SINT, &CopyNativeVertexData<GLbyte, 4, 4, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R8G8B8A8_SINT,
+ &CopyNativeVertexData<GLbyte, 4, 4, 0>);
return info;
}
// GL_BYTE -- normalized
case gl::VERTEX_FORMAT_SBYTE1_NORM:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R8_SNORM, &CopyNativeVertexData<GLbyte, 1, 1, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R8_SNORM,
+ &CopyNativeVertexData<GLbyte, 1, 1, 0>);
return info;
}
case gl::VERTEX_FORMAT_SBYTE2_NORM:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R8G8_SNORM, &CopyNativeVertexData<GLbyte, 2, 2, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R8G8_SNORM,
+ &CopyNativeVertexData<GLbyte, 2, 2, 0>);
return info;
}
case gl::VERTEX_FORMAT_SBYTE3_NORM:
{
- static const VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R8G8B8A8_SNORM, &CopyNativeVertexData<GLbyte, 3, 4, INT8_MAX>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R8G8B8A8_SNORM,
+ &CopyNativeVertexData<GLbyte, 3, 4, INT8_MAX>);
return info;
}
case gl::VERTEX_FORMAT_SBYTE4_NORM:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R8G8B8A8_SNORM, &CopyNativeVertexData<GLbyte, 4, 4, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R8G8B8A8_SNORM,
+ &CopyNativeVertexData<GLbyte, 4, 4, 0>);
return info;
}
// GL_UNSIGNED_BYTE -- un-normalized
case gl::VERTEX_FORMAT_UBYTE1:
{
- static const VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R8_UINT, &CopyNativeVertexData<GLubyte, 1, 1, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R8_UINT,
+ &CopyNativeVertexData<GLubyte, 1, 1, 0>);
return info;
}
case gl::VERTEX_FORMAT_UBYTE2:
{
- static const VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R8G8_UINT, &CopyNativeVertexData<GLubyte, 2, 2, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R8G8_UINT,
+ &CopyNativeVertexData<GLubyte, 2, 2, 0>);
return info;
}
case gl::VERTEX_FORMAT_UBYTE3:
{
- static const VertexFormat info(VERTEX_CONVERT_BOTH, DXGI_FORMAT_R8G8B8A8_UINT, &CopyNativeVertexData<GLubyte, 3, 4, 1>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_BOTH, DXGI_FORMAT_R8G8B8A8_UINT,
+ &CopyNativeVertexData<GLubyte, 3, 4, 1>);
return info;
}
case gl::VERTEX_FORMAT_UBYTE4:
{
- static const VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R8G8B8A8_UINT, &CopyNativeVertexData<GLubyte, 4, 4, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R8G8B8A8_UINT,
+ &CopyNativeVertexData<GLubyte, 4, 4, 0>);
return info;
}
// GL_UNSIGNED_BYTE -- normalized
case gl::VERTEX_FORMAT_UBYTE1_NORM:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R8_UNORM, &CopyNativeVertexData<GLubyte, 1, 1, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R8_UNORM,
+ &CopyNativeVertexData<GLubyte, 1, 1, 0>);
return info;
}
case gl::VERTEX_FORMAT_UBYTE2_NORM:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R8G8_UNORM, &CopyNativeVertexData<GLubyte, 2, 2, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R8G8_UNORM,
+ &CopyNativeVertexData<GLubyte, 2, 2, 0>);
return info;
}
case gl::VERTEX_FORMAT_UBYTE3_NORM:
{
- static const VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R8G8B8A8_UNORM, &CopyNativeVertexData<GLubyte, 3, 4, UINT8_MAX>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R8G8B8A8_UNORM,
+ &CopyNativeVertexData<GLubyte, 3, 4, UINT8_MAX>);
return info;
}
case gl::VERTEX_FORMAT_UBYTE4_NORM:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R8G8B8A8_UNORM, &CopyNativeVertexData<GLubyte, 4, 4, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R8G8B8A8_UNORM,
+ &CopyNativeVertexData<GLubyte, 4, 4, 0>);
return info;
}
// GL_SHORT -- un-normalized
case gl::VERTEX_FORMAT_SSHORT1:
{
- static const VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R16_SINT, &CopyNativeVertexData<GLshort, 1, 1, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R16_SINT,
+ &CopyNativeVertexData<GLshort, 1, 1, 0>);
return info;
}
case gl::VERTEX_FORMAT_SSHORT2:
{
- static const VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R16G16_SINT, &CopyNativeVertexData<GLshort, 2, 2, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R16G16_SINT,
+ &CopyNativeVertexData<GLshort, 2, 2, 0>);
return info;
}
case gl::VERTEX_FORMAT_SSHORT3:
{
- static const VertexFormat info(VERTEX_CONVERT_BOTH, DXGI_FORMAT_R16G16B16A16_SINT, &CopyNativeVertexData<GLshort, 3, 4, 1>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_BOTH, DXGI_FORMAT_R16G16B16A16_SINT,
+ &CopyNativeVertexData<GLshort, 3, 4, 1>);
return info;
}
case gl::VERTEX_FORMAT_SSHORT4:
{
- static const VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R16G16B16A16_SINT, &CopyNativeVertexData<GLshort, 4, 4, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R16G16B16A16_SINT,
+ &CopyNativeVertexData<GLshort, 4, 4, 0>);
return info;
}
// GL_SHORT -- normalized
case gl::VERTEX_FORMAT_SSHORT1_NORM:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16_SNORM, &CopyNativeVertexData<GLshort, 1, 1, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16_SNORM,
+ &CopyNativeVertexData<GLshort, 1, 1, 0>);
return info;
}
case gl::VERTEX_FORMAT_SSHORT2_NORM:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16G16_SNORM, &CopyNativeVertexData<GLshort, 2, 2, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16G16_SNORM,
+ &CopyNativeVertexData<GLshort, 2, 2, 0>);
return info;
}
case gl::VERTEX_FORMAT_SSHORT3_NORM:
{
- static const VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R16G16B16A16_SNORM, &CopyNativeVertexData<GLshort, 3, 4, INT16_MAX>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R16G16B16A16_SNORM,
+ &CopyNativeVertexData<GLshort, 3, 4, INT16_MAX>);
return info;
}
case gl::VERTEX_FORMAT_SSHORT4_NORM:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16G16B16A16_SNORM, &CopyNativeVertexData<GLshort, 4, 4, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16G16B16A16_SNORM,
+ &CopyNativeVertexData<GLshort, 4, 4, 0>);
return info;
}
// GL_UNSIGNED_SHORT -- un-normalized
case gl::VERTEX_FORMAT_USHORT1:
{
- static const VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R16_UINT, &CopyNativeVertexData<GLushort, 1, 1, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R16_UINT,
+ &CopyNativeVertexData<GLushort, 1, 1, 0>);
return info;
}
case gl::VERTEX_FORMAT_USHORT2:
{
- static const VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R16G16_UINT, &CopyNativeVertexData<GLushort, 2, 2, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R16G16_UINT,
+ &CopyNativeVertexData<GLushort, 2, 2, 0>);
return info;
}
case gl::VERTEX_FORMAT_USHORT3:
{
- static const VertexFormat info(VERTEX_CONVERT_BOTH, DXGI_FORMAT_R16G16B16A16_UINT, &CopyNativeVertexData<GLushort, 3, 4, 1>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_BOTH, DXGI_FORMAT_R16G16B16A16_UINT,
+ &CopyNativeVertexData<GLushort, 3, 4, 1>);
return info;
}
case gl::VERTEX_FORMAT_USHORT4:
{
- static const VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R16G16B16A16_UINT, &CopyNativeVertexData<GLushort, 4, 4, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R16G16B16A16_UINT,
+ &CopyNativeVertexData<GLushort, 4, 4, 0>);
return info;
}
// GL_UNSIGNED_SHORT -- normalized
case gl::VERTEX_FORMAT_USHORT1_NORM:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16_UNORM, &CopyNativeVertexData<GLushort, 1, 1, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16_UNORM,
+ &CopyNativeVertexData<GLushort, 1, 1, 0>);
return info;
}
case gl::VERTEX_FORMAT_USHORT2_NORM:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16G16_UNORM, &CopyNativeVertexData<GLushort, 2, 2, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16G16_UNORM,
+ &CopyNativeVertexData<GLushort, 2, 2, 0>);
return info;
}
case gl::VERTEX_FORMAT_USHORT3_NORM:
{
- static const VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R16G16B16A16_UNORM, &CopyNativeVertexData<GLushort, 3, 4, UINT16_MAX>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R16G16B16A16_UNORM,
+ &CopyNativeVertexData<GLushort, 3, 4, UINT16_MAX>);
return info;
}
case gl::VERTEX_FORMAT_USHORT4_NORM:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16G16B16A16_UNORM, &CopyNativeVertexData<GLushort, 4, 4, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16G16B16A16_UNORM,
+ &CopyNativeVertexData<GLushort, 4, 4, 0>);
return info;
}
// GL_INT -- un-normalized
case gl::VERTEX_FORMAT_SINT1:
{
- static const VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R32_SINT, &CopyNativeVertexData<GLint, 1, 1, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R32_SINT,
+ &CopyNativeVertexData<GLint, 1, 1, 0>);
return info;
}
case gl::VERTEX_FORMAT_SINT2:
{
- static const VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R32G32_SINT, &CopyNativeVertexData<GLint, 2, 2, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R32G32_SINT,
+ &CopyNativeVertexData<GLint, 2, 2, 0>);
return info;
}
case gl::VERTEX_FORMAT_SINT3:
{
- static const VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R32G32B32_SINT, &CopyNativeVertexData<GLint, 3, 3, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R32G32B32_SINT,
+ &CopyNativeVertexData<GLint, 3, 3, 0>);
return info;
}
case gl::VERTEX_FORMAT_SINT4:
{
- static const VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R32G32B32A32_SINT, &CopyNativeVertexData<GLint, 4, 4, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R32G32B32A32_SINT,
+ &CopyNativeVertexData<GLint, 4, 4, 0>);
return info;
}
// GL_INT -- normalized
case gl::VERTEX_FORMAT_SINT1_NORM:
{
- static const VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32_FLOAT, &CopyTo32FVertexData<GLint, 1, 1, true>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32_FLOAT,
+ &CopyTo32FVertexData<GLint, 1, 1, true>);
return info;
}
case gl::VERTEX_FORMAT_SINT2_NORM:
{
- static const VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32_FLOAT, &CopyTo32FVertexData<GLint, 2, 2, true>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32_FLOAT,
+ &CopyTo32FVertexData<GLint, 2, 2, true>);
return info;
}
case gl::VERTEX_FORMAT_SINT3_NORM:
{
- static const VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32B32_FLOAT, &CopyTo32FVertexData<GLint, 3, 3, true>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32B32_FLOAT,
+ &CopyTo32FVertexData<GLint, 3, 3, true>);
return info;
}
case gl::VERTEX_FORMAT_SINT4_NORM:
{
- static const VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32B32A32_FLOAT, &CopyTo32FVertexData<GLint, 4, 4, true>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32B32A32_FLOAT,
+ &CopyTo32FVertexData<GLint, 4, 4, true>);
return info;
}
// GL_UNSIGNED_INT -- un-normalized
case gl::VERTEX_FORMAT_UINT1:
{
- static const VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R32_UINT, &CopyNativeVertexData<GLuint, 1, 1, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R32_UINT,
+ &CopyNativeVertexData<GLuint, 1, 1, 0>);
return info;
}
case gl::VERTEX_FORMAT_UINT2:
{
- static const VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R32G32_UINT, &CopyNativeVertexData<GLuint, 2, 2, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R32G32_UINT,
+ &CopyNativeVertexData<GLuint, 2, 2, 0>);
return info;
}
case gl::VERTEX_FORMAT_UINT3:
{
- static const VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R32G32B32_UINT, &CopyNativeVertexData<GLuint, 3, 3, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R32G32B32_UINT,
+ &CopyNativeVertexData<GLuint, 3, 3, 0>);
return info;
}
case gl::VERTEX_FORMAT_UINT4:
{
- static const VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R32G32B32A32_UINT, &CopyNativeVertexData<GLuint, 4, 4, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_GPU, DXGI_FORMAT_R32G32B32A32_UINT,
+ &CopyNativeVertexData<GLuint, 4, 4, 0>);
return info;
}
// GL_UNSIGNED_INT -- normalized
case gl::VERTEX_FORMAT_UINT1_NORM:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R32_FLOAT, &CopyTo32FVertexData<GLuint, 1, 1, true>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32_FLOAT,
+ &CopyTo32FVertexData<GLuint, 1, 1, true>);
return info;
}
case gl::VERTEX_FORMAT_UINT2_NORM:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R32G32_FLOAT, &CopyTo32FVertexData<GLuint, 2, 2, true>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32_FLOAT,
+ &CopyTo32FVertexData<GLuint, 2, 2, true>);
return info;
}
case gl::VERTEX_FORMAT_UINT3_NORM:
{
- static const VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32B32_FLOAT, &CopyTo32FVertexData<GLuint, 3, 3, true>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32B32_FLOAT,
+ &CopyTo32FVertexData<GLuint, 3, 3, true>);
return info;
}
case gl::VERTEX_FORMAT_UINT4_NORM:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R32G32B32A32_FLOAT, &CopyTo32FVertexData<GLuint, 4, 4, true>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32B32A32_FLOAT,
+ &CopyTo32FVertexData<GLuint, 4, 4, true>);
return info;
}
// GL_FIXED
case gl::VERTEX_FORMAT_FIXED1:
{
- static const VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32_FLOAT, &Copy32FixedTo32FVertexData<1, 1>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32_FLOAT,
+ &Copy32FixedTo32FVertexData<1, 1>);
return info;
}
case gl::VERTEX_FORMAT_FIXED2:
{
- static const VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32_FLOAT, &Copy32FixedTo32FVertexData<2, 2>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32_FLOAT,
+ &Copy32FixedTo32FVertexData<2, 2>);
return info;
}
case gl::VERTEX_FORMAT_FIXED3:
{
- static const VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32B32_FLOAT, &Copy32FixedTo32FVertexData<3, 3>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32B32_FLOAT,
+ &Copy32FixedTo32FVertexData<3, 3>);
return info;
}
case gl::VERTEX_FORMAT_FIXED4:
{
- static const VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32B32A32_FLOAT, &Copy32FixedTo32FVertexData<4, 4>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32B32A32_FLOAT,
+ &Copy32FixedTo32FVertexData<4, 4>);
return info;
}
// GL_HALF_FLOAT
case gl::VERTEX_FORMAT_HALF1:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16_FLOAT, &CopyNativeVertexData<GLhalf, 1, 1, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16_FLOAT,
+ &CopyNativeVertexData<GLhalf, 1, 1, 0>);
return info;
}
case gl::VERTEX_FORMAT_HALF2:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16G16_FLOAT, &CopyNativeVertexData<GLhalf, 2, 2, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16G16_FLOAT,
+ &CopyNativeVertexData<GLhalf, 2, 2, 0>);
return info;
}
case gl::VERTEX_FORMAT_HALF3:
{
- static const VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R16G16B16A16_FLOAT, &CopyNativeVertexData<GLhalf, 3, 4, gl::Float16One>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R16G16B16A16_FLOAT,
+ &CopyNativeVertexData<GLhalf, 3, 4, gl::Float16One>);
return info;
}
case gl::VERTEX_FORMAT_HALF4:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16G16B16A16_FLOAT, &CopyNativeVertexData<GLhalf, 4, 4, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16G16B16A16_FLOAT,
+ &CopyNativeVertexData<GLhalf, 4, 4, 0>);
return info;
}
// GL_FLOAT
case gl::VERTEX_FORMAT_FLOAT1:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R32_FLOAT, &CopyNativeVertexData<GLfloat, 1, 1, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R32_FLOAT,
+ &CopyNativeVertexData<GLfloat, 1, 1, 0>);
return info;
}
case gl::VERTEX_FORMAT_FLOAT2:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R32G32_FLOAT, &CopyNativeVertexData<GLfloat, 2, 2, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R32G32_FLOAT,
+ &CopyNativeVertexData<GLfloat, 2, 2, 0>);
return info;
}
case gl::VERTEX_FORMAT_FLOAT3:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R32G32B32_FLOAT, &CopyNativeVertexData<GLfloat, 3, 3, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R32G32B32_FLOAT,
+ &CopyNativeVertexData<GLfloat, 3, 3, 0>);
return info;
}
case gl::VERTEX_FORMAT_FLOAT4:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R32G32B32A32_FLOAT, &CopyNativeVertexData<GLfloat, 4, 4, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R32G32B32A32_FLOAT,
+ &CopyNativeVertexData<GLfloat, 4, 4, 0>);
return info;
}
// GL_INT_2_10_10_10_REV
case gl::VERTEX_FORMAT_SINT210:
{
- static const VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32B32A32_FLOAT, &CopyXYZ10W2ToXYZW32FVertexData<true, false, true>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32B32A32_FLOAT,
+ &CopyXYZ10W2ToXYZW32FVertexData<true, false, true>);
return info;
}
case gl::VERTEX_FORMAT_SINT210_NORM:
{
- static const VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32B32A32_FLOAT, &CopyXYZ10W2ToXYZW32FVertexData<true, true, true>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32B32A32_FLOAT,
+ &CopyXYZ10W2ToXYZW32FVertexData<true, true, true>);
return info;
}
// GL_UNSIGNED_INT_2_10_10_10_REV
case gl::VERTEX_FORMAT_UINT210:
{
- static const VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32B32A32_FLOAT, &CopyXYZ10W2ToXYZW32FVertexData<false, false, true>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R32G32B32A32_FLOAT,
+ &CopyXYZ10W2ToXYZW32FVertexData<false, false, true>);
return info;
}
case gl::VERTEX_FORMAT_UINT210_NORM:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R10G10B10A2_UNORM, &CopyNativeVertexData<GLuint, 1, 1, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R10G10B10A2_UNORM,
+ &CopyNativeVertexData<GLuint, 1, 1, 0>);
return info;
}
@@ -947,157 +841,183 @@ const VertexFormat &GetVertexFormatInfo(gl::VertexFormatType vertexFormatType, D
// GL_BYTE
case gl::VERTEX_FORMAT_SBYTE1_INT:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R8_SINT, &CopyNativeVertexData<GLbyte, 1, 1, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R8_SINT,
+ &CopyNativeVertexData<GLbyte, 1, 1, 0>);
return info;
}
case gl::VERTEX_FORMAT_SBYTE2_INT:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R8G8_SINT, &CopyNativeVertexData<GLbyte, 2, 2, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R8G8_SINT,
+ &CopyNativeVertexData<GLbyte, 2, 2, 0>);
return info;
}
case gl::VERTEX_FORMAT_SBYTE3_INT:
{
- static const VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R8G8B8A8_SINT, &CopyNativeVertexData<GLbyte, 3, 4, 1>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R8G8B8A8_SINT,
+ &CopyNativeVertexData<GLbyte, 3, 4, 1>);
return info;
}
case gl::VERTEX_FORMAT_SBYTE4_INT:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R8G8B8A8_SINT, &CopyNativeVertexData<GLbyte, 4, 4, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R8G8B8A8_SINT,
+ &CopyNativeVertexData<GLbyte, 4, 4, 0>);
return info;
}
// GL_UNSIGNED_BYTE
case gl::VERTEX_FORMAT_UBYTE1_INT:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R8_UINT, &CopyNativeVertexData<GLubyte, 1, 1, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R8_UINT,
+ &CopyNativeVertexData<GLubyte, 1, 1, 0>);
return info;
}
case gl::VERTEX_FORMAT_UBYTE2_INT:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R8G8_UINT, &CopyNativeVertexData<GLubyte, 2, 2, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R8G8_UINT,
+ &CopyNativeVertexData<GLubyte, 2, 2, 0>);
return info;
}
case gl::VERTEX_FORMAT_UBYTE3_INT:
{
- static const VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R8G8B8A8_UINT, &CopyNativeVertexData<GLubyte, 3, 4, 1>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R8G8B8A8_UINT,
+ &CopyNativeVertexData<GLubyte, 3, 4, 1>);
return info;
}
case gl::VERTEX_FORMAT_UBYTE4_INT:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R8G8B8A8_UINT, &CopyNativeVertexData<GLubyte, 4, 4, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R8G8B8A8_UINT,
+ &CopyNativeVertexData<GLubyte, 4, 4, 0>);
return info;
}
// GL_SHORT
case gl::VERTEX_FORMAT_SSHORT1_INT:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16_SINT, &CopyNativeVertexData<GLshort, 1, 1, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16_SINT,
+ &CopyNativeVertexData<GLshort, 1, 1, 0>);
return info;
}
case gl::VERTEX_FORMAT_SSHORT2_INT:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16G16_SINT, &CopyNativeVertexData<GLshort, 2, 2, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16G16_SINT,
+ &CopyNativeVertexData<GLshort, 2, 2, 0>);
return info;
}
case gl::VERTEX_FORMAT_SSHORT3_INT:
{
- static const VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R16G16B16A16_SINT, &CopyNativeVertexData<GLshort, 3, 4, 1>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R16G16B16A16_SINT,
+ &CopyNativeVertexData<GLshort, 3, 4, 1>);
return info;
}
case gl::VERTEX_FORMAT_SSHORT4_INT:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16G16B16A16_SINT, &CopyNativeVertexData<GLshort, 4, 4, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16G16B16A16_SINT,
+ &CopyNativeVertexData<GLshort, 4, 4, 0>);
return info;
}
// GL_UNSIGNED_SHORT
case gl::VERTEX_FORMAT_USHORT1_INT:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16_UINT, &CopyNativeVertexData<GLushort, 1, 1, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16_UINT,
+ &CopyNativeVertexData<GLushort, 1, 1, 0>);
return info;
}
case gl::VERTEX_FORMAT_USHORT2_INT:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16G16_UINT, &CopyNativeVertexData<GLushort, 2, 2, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16G16_UINT,
+ &CopyNativeVertexData<GLushort, 2, 2, 0>);
return info;
}
case gl::VERTEX_FORMAT_USHORT3_INT:
{
- static const VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R16G16B16A16_UINT, &CopyNativeVertexData<GLushort, 3, 4, 1>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R16G16B16A16_UINT,
+ &CopyNativeVertexData<GLushort, 3, 4, 1>);
return info;
}
case gl::VERTEX_FORMAT_USHORT4_INT:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16G16B16A16_UINT, &CopyNativeVertexData<GLushort, 4, 4, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R16G16B16A16_UINT,
+ &CopyNativeVertexData<GLushort, 4, 4, 0>);
return info;
}
// GL_INT
case gl::VERTEX_FORMAT_SINT1_INT:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R32_SINT, &CopyNativeVertexData<GLint, 1, 1, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R32_SINT,
+ &CopyNativeVertexData<GLint, 1, 1, 0>);
return info;
}
case gl::VERTEX_FORMAT_SINT2_INT:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R32G32_SINT, &CopyNativeVertexData<GLint, 2, 2, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R32G32_SINT,
+ &CopyNativeVertexData<GLint, 2, 2, 0>);
return info;
}
case gl::VERTEX_FORMAT_SINT3_INT:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R32G32B32_SINT, &CopyNativeVertexData<GLint, 3, 3, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R32G32B32_SINT,
+ &CopyNativeVertexData<GLint, 3, 3, 0>);
return info;
}
case gl::VERTEX_FORMAT_SINT4_INT:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R32G32B32A32_SINT, &CopyNativeVertexData<GLint, 4, 4, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R32G32B32A32_SINT,
+ &CopyNativeVertexData<GLint, 4, 4, 0>);
return info;
}
// GL_UNSIGNED_INT
case gl::VERTEX_FORMAT_UINT1_INT:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R32_SINT, &CopyNativeVertexData<GLuint, 1, 1, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R32_SINT,
+ &CopyNativeVertexData<GLuint, 1, 1, 0>);
return info;
}
case gl::VERTEX_FORMAT_UINT2_INT:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R32G32_SINT, &CopyNativeVertexData<GLuint, 2, 2, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R32G32_SINT,
+ &CopyNativeVertexData<GLuint, 2, 2, 0>);
return info;
}
case gl::VERTEX_FORMAT_UINT3_INT:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R32G32B32_SINT, &CopyNativeVertexData<GLuint, 3, 3, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R32G32B32_SINT,
+ &CopyNativeVertexData<GLuint, 3, 3, 0>);
return info;
}
case gl::VERTEX_FORMAT_UINT4_INT:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R32G32B32A32_SINT, &CopyNativeVertexData<GLuint, 4, 4, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R32G32B32A32_SINT,
+ &CopyNativeVertexData<GLuint, 4, 4, 0>);
return info;
}
// GL_INT_2_10_10_10_REV
case gl::VERTEX_FORMAT_SINT210_INT:
{
- static const VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R16G16B16A16_SINT, &CopyXYZ10W2ToXYZW32FVertexData<true, true, false>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_CPU, DXGI_FORMAT_R16G16B16A16_SINT,
+ &CopyXYZ10W2ToXYZW32FVertexData<true, true, false>);
return info;
}
// GL_UNSIGNED_INT_2_10_10_10_REV
case gl::VERTEX_FORMAT_UINT210_INT:
{
- static const VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R10G10B10A2_UINT, &CopyNativeVertexData<GLuint, 1, 1, 0>);
+ static constexpr VertexFormat info(VERTEX_CONVERT_NONE, DXGI_FORMAT_R10G10B10A2_UINT,
+ &CopyNativeVertexData<GLuint, 1, 1, 0>);
return info;
}
default:
{
- static const VertexFormat info;
+ static constexpr VertexFormat info;
return info;
}
}
}
-}
+} // namespace d3d11
-}
+} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/formatutils11.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/formatutils11.h
index 7b97527140..883d338377 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/formatutils11.h
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/formatutils11.h
@@ -15,6 +15,7 @@
#include "common/platform.h"
#include "libANGLE/angletypes.h"
#include "libANGLE/formatutils.h"
+#include "libANGLE/renderer/renderer_utils.h"
#include "libANGLE/renderer/d3d/formatutilsD3D.h"
namespace rx
@@ -24,58 +25,47 @@ struct Renderer11DeviceCaps;
namespace d3d11
{
-typedef std::map<std::pair<GLenum, GLenum>, ColorCopyFunction> FastCopyFunctionMap;
-typedef bool (*NativeMipmapGenerationSupportFunction)(D3D_FEATURE_LEVEL);
+// A texture might be stored as DXGI_FORMAT_R16_TYPELESS but store integer components,
+// which are accessed through an DXGI_FORMAT_R16_SINT view. It's easy to write code which queries
+// information about the wrong format. Therefore, use of this should be avoided where possible.
-struct DXGIFormat
+bool SupportsMipGen(DXGI_FORMAT dxgiFormat, D3D_FEATURE_LEVEL featureLevel);
+
+struct DXGIFormatSize
{
- DXGIFormat();
+ DXGIFormatSize(GLuint pixelBits, GLuint blockWidth, GLuint blockHeight);
GLuint pixelBytes;
GLuint blockWidth;
GLuint blockHeight;
-
- GLuint redBits;
- GLuint greenBits;
- GLuint blueBits;
- GLuint alphaBits;
- GLuint sharedBits;
-
- GLuint depthBits;
- GLuint depthOffset;
- GLuint stencilBits;
- GLuint stencilOffset;
-
- GLenum internalFormat;
- GLenum componentType;
-
- MipGenerationFunction mipGenerationFunction;
- ColorReadFunction colorReadFunction;
-
- FastCopyFunctionMap fastCopyFunctions;
-
- NativeMipmapGenerationSupportFunction nativeMipmapSupport;
-
- ColorCopyFunction getFastCopyFunction(GLenum format, GLenum type) const;
};
-const DXGIFormat &GetDXGIFormatInfo(DXGI_FORMAT format);
+const DXGIFormatSize &GetDXGIFormatSizeInfo(DXGI_FORMAT format);
-struct VertexFormat
+struct VertexFormat : private angle::NonCopyable
{
- VertexFormat();
- VertexFormat(VertexConversionType conversionType,
- DXGI_FORMAT nativeFormat,
- VertexCopyFunction copyFunction);
+ constexpr VertexFormat();
+ constexpr VertexFormat(VertexConversionType conversionType,
+ DXGI_FORMAT nativeFormat,
+ VertexCopyFunction copyFunction);
VertexConversionType conversionType;
DXGI_FORMAT nativeFormat;
VertexCopyFunction copyFunction;
};
+
const VertexFormat &GetVertexFormatInfo(gl::VertexFormatType vertexFormatType,
D3D_FEATURE_LEVEL featureLevel);
+// Auto-generated in dxgi_format_map_autogen.cpp.
+GLenum GetComponentType(DXGI_FORMAT dxgiFormat);
+
} // namespace d3d11
+namespace d3d11_angle
+{
+const angle::Format &GetFormat(DXGI_FORMAT dxgiFormat);
+}
+
} // namespace rx
#endif // LIBANGLE_RENDERER_D3D_D3D11_FORMATUTILS11_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/gen_load_functions_table.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/gen_load_functions_table.cpp
deleted file mode 100644
index e69de29bb2..0000000000
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/gen_load_functions_table.cpp
+++ /dev/null
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/internal_format_initializer_table.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/internal_format_initializer_table.cpp
deleted file mode 100644
index adb20a5e60..0000000000
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/internal_format_initializer_table.cpp
+++ /dev/null
@@ -1,170 +0,0 @@
-//
-// Copyright 2015 The ANGLE Project Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-//
-// internal_format_initializer_table:
-// Contains table to go from internal format and dxgi format to initializer function
-// for TextureFormat
-//
-
-#include "libANGLE/renderer/d3d/d3d11/internal_format_initializer_table.h"
-#include "libANGLE/renderer/d3d/loadimage.h"
-
-namespace rx
-{
-
-namespace d3d11
-{
-
-// TODO: This should be generated by a JSON file
-InitializeTextureDataFunction GetInternalFormatInitializer(GLenum internalFormat,
- DXGI_FORMAT dxgiFormat)
-{
- switch (internalFormat)
- {
- case GL_RGB8:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8G8B8A8_UNORM:
- {
- return Initialize4ComponentData<GLubyte, 0x00, 0x00, 0x00, 0xFF>;
- }
- default:
- break;
- }
- }
- case GL_RGB565:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8G8B8A8_UNORM:
- {
- return Initialize4ComponentData<GLubyte, 0x00, 0x00, 0x00, 0xFF>;
- }
- default:
- break;
- }
- }
- case GL_SRGB8:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB:
- {
- return Initialize4ComponentData<GLubyte, 0x00, 0x00, 0x00, 0xFF>;
- }
- default:
- break;
- }
- }
- case GL_RGB16F:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R16G16B16A16_FLOAT:
- {
- return Initialize4ComponentData<GLhalf, 0x0000, 0x0000, 0x0000, gl::Float16One>;
- }
- default:
- break;
- }
- }
- case GL_RGB32F:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R32G32B32A32_FLOAT:
- {
- return Initialize4ComponentData<GLfloat, 0x00000000, 0x00000000, 0x00000000,
- gl::Float32One>;
- }
- default:
- break;
- }
- }
- case GL_RGB8UI:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8G8B8A8_UINT:
- {
- return Initialize4ComponentData<GLubyte, 0x00, 0x00, 0x00, 0x01>;
- }
- default:
- break;
- }
- }
- case GL_RGB8I:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8G8B8A8_SINT:
- {
- return Initialize4ComponentData<GLbyte, 0x00, 0x00, 0x00, 0x01>;
- }
- default:
- break;
- }
- }
- case GL_RGB16UI:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R16G16B16A16_UINT:
- {
- return Initialize4ComponentData<GLushort, 0x0000, 0x0000, 0x0000, 0x0001>;
- }
- default:
- break;
- }
- }
- case GL_RGB16I:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R16G16B16A16_SINT:
- {
- return Initialize4ComponentData<GLshort, 0x0000, 0x0000, 0x0000, 0x0001>;
- }
- default:
- break;
- }
- }
- case GL_RGB32UI:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R32G32B32A32_UINT:
- {
- return Initialize4ComponentData<GLuint, 0x00000000, 0x00000000, 0x00000000,
- 0x00000001>;
- }
- default:
- break;
- }
- }
- case GL_RGB32I:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R32G32B32A32_SINT:
- {
- return Initialize4ComponentData<GLint, 0x00000000, 0x00000000, 0x00000000,
- 0x00000001>;
- }
- default:
- break;
- }
- }
- default:
- {
- return nullptr;
- }
- }
-}
-
-} // namespace d3d11
-
-} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/internal_format_initializer_table.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/internal_format_initializer_table.h
deleted file mode 100644
index 2d538e1d82..0000000000
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/internal_format_initializer_table.h
+++ /dev/null
@@ -1,31 +0,0 @@
-//
-// Copyright 2015 The ANGLE Project Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-//
-// internal_format_initializer_table:
-// Contains table to go from internal format and dxgi format to initializer function
-// for TextureFormat
-//
-
-#ifndef LIBANGLE_RENDERER_D3D_D3D11_INTERNALFORMATINITIALIZERTABLE_H_
-#define LIBANGLE_RENDERER_D3D_D3D11_INTERNALFORMATINITIALIZERTABLE_H_
-
-#include "libANGLE/renderer/d3d/d3d11/Renderer11.h"
-
-#include <map>
-
-namespace rx
-{
-
-namespace d3d11
-{
-
-InitializeTextureDataFunction GetInternalFormatInitializer(GLenum internalFormat,
- DXGI_FORMAT dxgiFormat);
-
-} // namespace d3d11
-
-} // namespace rx
-
-#endif // LIBANGLE_RENDERER_D3D_D3D11_INTERNALFORMATINITIALIZERTABLE_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/load_functions_data.json b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/load_functions_data.json
deleted file mode 100644
index c85393e06b..0000000000
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/load_functions_data.json
+++ /dev/null
@@ -1,1116 +0,0 @@
-{
- "GL_RG8_SNORM": {
- "GL_BYTE": [
- {
- "loadFunction": "LoadToNative<GLbyte,2>",
- "dxgiFormat": "DXGI_FORMAT_R8G8_SNORM",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_SRGB8": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadToNative3To4<GLubyte,0xFF>",
- "dxgiFormat": "DXGI_FORMAT_R8G8B8A8_UNORM_SRGB",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_RGBA8I": {
- "GL_BYTE": [
- {
- "loadFunction": "LoadToNative<GLbyte,4>",
- "dxgiFormat": "DXGI_FORMAT_R8G8B8A8_SINT",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_R8_SNORM": {
- "GL_BYTE": [
- {
- "loadFunction": "LoadToNative<GLbyte,1>",
- "dxgiFormat": "DXGI_FORMAT_R8_SNORM",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_RGBA8_SNORM": {
- "GL_BYTE": [
- {
- "loadFunction": "LoadToNative<GLbyte,4>",
- "dxgiFormat": "DXGI_FORMAT_R8G8B8A8_SNORM",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_R16I": {
- "GL_SHORT": [
- {
- "loadFunction": "LoadToNative<GLshort,1>",
- "dxgiFormat": "DXGI_FORMAT_R16_SINT",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_COMPRESSED_SRGB8_ALPHA8_ETC2_EAC": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadETC2SRGBA8ToSRGBA8",
- "dxgiFormat": "DXGI_FORMAT_R8G8B8A8_UNORM_SRGB",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_COMPRESSED_RGB8_PUNCHTHROUGH_ALPHA1_ETC2": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadETC2RGB8A1ToRGBA8",
- "dxgiFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_RGB32UI": {
- "GL_UNSIGNED_INT": [
- {
- "loadFunction": "LoadToNative3To4<GLuint,0x00000001>",
- "dxgiFormat": "DXGI_FORMAT_R32G32B32A32_UINT",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_ALPHA32F_EXT": {
- "GL_FLOAT": [
- {
- "loadFunction": "LoadA32FToRGBA32F",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_R16UI": {
- "GL_UNSIGNED_SHORT": [
- {
- "loadFunction": "LoadToNative<GLushort,1>",
- "dxgiFormat": "DXGI_FORMAT_R16_UINT",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_RGB9_E5": {
- "GL_HALF_FLOAT": [
- {
- "loadFunction": "LoadRGB16FToRGB9E5",
- "dxgiFormat": "DXGI_FORMAT_R9G9B9E5_SHAREDEXP",
- "requiresConversion": "true"
- }
- ],
- "GL_UNSIGNED_INT_5_9_9_9_REV": [
- {
- "loadFunction": "LoadToNative<GLuint,1>",
- "dxgiFormat": "DXGI_FORMAT_R9G9B9E5_SHAREDEXP",
- "requiresConversion": "false"
- }
- ],
- "GL_FLOAT": [
- {
- "loadFunction": "LoadRGB32FToRGB9E5",
- "dxgiFormat": "DXGI_FORMAT_R9G9B9E5_SHAREDEXP",
- "requiresConversion": "true"
- }
- ],
- "GL_HALF_FLOAT_OES": [
- {
- "loadFunction": "LoadRGB16FToRGB9E5",
- "dxgiFormat": "DXGI_FORMAT_R9G9B9E5_SHAREDEXP",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_COMPRESSED_R11_EAC": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadEACR11ToR8",
- "dxgiFormat": "DXGI_FORMAT_R8_UNORM",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_RGBA32UI": {
- "GL_UNSIGNED_INT": [
- {
- "loadFunction": "LoadToNative<GLuint,4>",
- "dxgiFormat": "DXGI_FORMAT_R32G32B32A32_UINT",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_RG8UI": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadToNative<GLubyte,2>",
- "dxgiFormat": "DXGI_FORMAT_R8G8_UINT",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_LUMINANCE32F_EXT": {
- "GL_FLOAT": [
- {
- "loadFunction": "LoadL32FToRGBA32F",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_COMPRESSED_SRGB8_PUNCHTHROUGH_ALPHA1_ETC2": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadETC2SRGB8A1ToRGBA8",
- "dxgiFormat": "DXGI_FORMAT_R8G8B8A8_UNORM_SRGB",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_R16F": {
- "GL_HALF_FLOAT": [
- {
- "loadFunction": "LoadToNative<GLhalf,1>",
- "dxgiFormat": "DXGI_FORMAT_R16_FLOAT",
- "requiresConversion": "false"
- }
- ],
- "GL_FLOAT": [
- {
- "loadFunction": "Load32FTo16F<1>",
- "dxgiFormat": "DXGI_FORMAT_R16_FLOAT",
- "requiresConversion": "true"
- }
- ],
- "GL_HALF_FLOAT_OES": [
- {
- "loadFunction": "LoadToNative<GLhalf,1>",
- "dxgiFormat": "DXGI_FORMAT_R16_FLOAT",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_RGBA8UI": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadToNative<GLubyte,4>",
- "dxgiFormat": "DXGI_FORMAT_R8G8B8A8_UINT",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_BGRA4_ANGLEX": {
- "GL_UNSIGNED_SHORT_4_4_4_4_REV_EXT": [
- {
- "loadFunction": "LoadRGBA4ToRGBA8",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ],
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadToNative<GLubyte,4>",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_RGBA16F": {
- "GL_HALF_FLOAT": [
- {
- "loadFunction": "LoadToNative<GLhalf,4>",
- "dxgiFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT",
- "requiresConversion": "false"
- }
- ],
- "GL_FLOAT": [
- {
- "loadFunction": "Load32FTo16F<4>",
- "dxgiFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT",
- "requiresConversion": "true"
- }
- ],
- "GL_HALF_FLOAT_OES": [
- {
- "loadFunction": "LoadToNative<GLhalf,4>",
- "dxgiFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_LUMINANCE8_EXT": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadL8ToRGBA8",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_COMPRESSED_RGBA_S3TC_DXT5_ANGLE": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadCompressedToNative<4,4,16>",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_RGB": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "UnreachableLoadFunction",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ],
- "GL_UNSIGNED_SHORT_5_6_5": [
- {
- "loadFunction": "UnreachableLoadFunction",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_RGB5_A1": {
- "GL_UNSIGNED_INT_2_10_10_10_REV": [
- {
- "loadFunction": "LoadRGB10A2ToRGBA8",
- "dxgiFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "requiresConversion": "true"
- }
- ],
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadToNative<GLubyte,4>",
- "dxgiFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "requiresConversion": "false"
- }
- ],
- "GL_UNSIGNED_SHORT_5_5_5_1": [
- {
- "loadFunction": "LoadRGB5A1ToRGBA8",
- "dxgiFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "requiresConversion": "true"
- },
- {
- "loadFunction": "LoadRGB5A1ToA1RGB5",
- "dxgiFormat": "DXGI_FORMAT_B5G5R5A1_UNORM",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_RGB16UI": {
- "GL_UNSIGNED_SHORT": [
- {
- "loadFunction": "LoadToNative3To4<GLushort,0x0001>",
- "dxgiFormat": "DXGI_FORMAT_R16G16B16A16_UINT",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_BGRA_EXT": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "UnreachableLoadFunction",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_COMPRESSED_RGB8_ETC2": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadETC2RGB8ToRGBA8",
- "dxgiFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_RGBA32F": {
- "GL_FLOAT": [
- {
- "loadFunction": "LoadToNative<GLfloat,4>",
- "dxgiFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_RGBA32I": {
- "GL_INT": [
- {
- "loadFunction": "LoadToNative<GLint,4>",
- "dxgiFormat": "DXGI_FORMAT_R32G32B32A32_SINT",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_LUMINANCE8_ALPHA8_EXT": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadLA8ToRGBA8",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_RG8": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadToNative<GLubyte,2>",
- "dxgiFormat": "DXGI_FORMAT_R8G8_UNORM",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_RGB10_A2": {
- "GL_UNSIGNED_INT_2_10_10_10_REV": [
- {
- "loadFunction": "LoadToNative<GLuint,1>",
- "dxgiFormat": "DXGI_FORMAT_R10G10B10A2_UNORM",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_COMPRESSED_SIGNED_RG11_EAC": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadEACRG11SToRG8",
- "dxgiFormat": "DXGI_FORMAT_R8G8_SNORM",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_DEPTH_COMPONENT16": {
- "GL_UNSIGNED_INT": [
- {
- "loadFunction": "LoadR32ToR16",
- "dxgiFormat": "DXGI_FORMAT_R16_TYPELESS",
- "requiresConversion": "true"
- }
- ],
- "GL_UNSIGNED_SHORT": [
- {
- "loadFunction": "LoadToNative<GLushort,1>",
- "dxgiFormat": "DXGI_FORMAT_R16_TYPELESS",
- "requiresConversion": "false"
- },
- {
- "loadFunction": "LoadToNative<GLushort,1>",
- "dxgiFormat": "DXGI_FORMAT_D16_UNORM",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_RGB32I": {
- "GL_INT": [
- {
- "loadFunction": "LoadToNative3To4<GLint,0x00000001>",
- "dxgiFormat": "DXGI_FORMAT_R32G32B32A32_SINT",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_R8": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadToNative<GLubyte,1>",
- "dxgiFormat": "DXGI_FORMAT_R8_UNORM",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_RGB32F": {
- "GL_FLOAT": [
- {
- "loadFunction": "LoadToNative3To4<GLfloat,gl::Float32One>",
- "dxgiFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_R11F_G11F_B10F": {
- "GL_UNSIGNED_INT_10F_11F_11F_REV": [
- {
- "loadFunction": "LoadToNative<GLuint,1>",
- "dxgiFormat": "DXGI_FORMAT_R11G11B10_FLOAT",
- "requiresConversion": "false"
- }
- ],
- "GL_HALF_FLOAT": [
- {
- "loadFunction": "LoadRGB16FToRG11B10F",
- "dxgiFormat": "DXGI_FORMAT_R11G11B10_FLOAT",
- "requiresConversion": "true"
- }
- ],
- "GL_FLOAT": [
- {
- "loadFunction": "LoadRGB32FToRG11B10F",
- "dxgiFormat": "DXGI_FORMAT_R11G11B10_FLOAT",
- "requiresConversion": "true"
- }
- ],
- "GL_HALF_FLOAT_OES": [
- {
- "loadFunction": "LoadRGB16FToRG11B10F",
- "dxgiFormat": "DXGI_FORMAT_R11G11B10_FLOAT",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_RGB8": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadToNative3To4<GLubyte,0xFF>",
- "dxgiFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_LUMINANCE_ALPHA": {
- "GL_HALF_FLOAT": [
- {
- "loadFunction": "LoadLA16FToRGBA16F",
- "dxgiFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT",
- "requiresConversion": "true"
- }
- ],
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "UnreachableLoadFunction",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ],
- "GL_FLOAT": [
- {
- "loadFunction": "LoadLA32FToRGBA32F",
- "dxgiFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT",
- "requiresConversion": "true"
- }
- ],
- "GL_HALF_FLOAT_OES": [
- {
- "loadFunction": "LoadLA16FToRGBA16F",
- "dxgiFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_RGBA16I": {
- "GL_SHORT": [
- {
- "loadFunction": "LoadToNative<GLshort,4>",
- "dxgiFormat": "DXGI_FORMAT_R16G16B16A16_SINT",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_R8I": {
- "GL_BYTE": [
- {
- "loadFunction": "LoadToNative<GLbyte,1>",
- "dxgiFormat": "DXGI_FORMAT_R8_SINT",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_RGB8_SNORM": {
- "GL_BYTE": [
- {
- "loadFunction": "LoadToNative3To4<GLbyte,0x7F>",
- "dxgiFormat": "DXGI_FORMAT_R8G8B8A8_SNORM",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_RG32F": {
- "GL_FLOAT": [
- {
- "loadFunction": "LoadToNative<GLfloat,2>",
- "dxgiFormat": "DXGI_FORMAT_R32G32_FLOAT",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_DEPTH_COMPONENT32F": {
- "GL_FLOAT": [
- {
- "loadFunction": "LoadToNative<GLfloat,1>",
- "dxgiFormat": "DXGI_FORMAT_R32_TYPELESS",
- "requiresConversion": "false"
- },
- {
- "loadFunction": "UnimplementedLoadFunction",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_RG32I": {
- "GL_INT": [
- {
- "loadFunction": "LoadToNative<GLint,2>",
- "dxgiFormat": "DXGI_FORMAT_R32G32_SINT",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_ALPHA8_EXT": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadToNative<GLubyte,1>",
- "dxgiFormat": "DXGI_FORMAT_A8_UNORM",
- "requiresConversion": "false"
- },
- {
- "loadFunction": "LoadA8ToRGBA8",
- "dxgiFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_RG32UI": {
- "GL_UNSIGNED_INT": [
- {
- "loadFunction": "LoadToNative<GLuint,2>",
- "dxgiFormat": "DXGI_FORMAT_R32G32_UINT",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_RGBA16UI": {
- "GL_UNSIGNED_SHORT": [
- {
- "loadFunction": "LoadToNative<GLushort,4>",
- "dxgiFormat": "DXGI_FORMAT_R16G16B16A16_UINT",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_COMPRESSED_RGBA8_ETC2_EAC": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadETC2RGBA8ToRGBA8",
- "dxgiFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_RGB8I": {
- "GL_BYTE": [
- {
- "loadFunction": "LoadToNative3To4<GLbyte,0x01>",
- "dxgiFormat": "DXGI_FORMAT_R8G8B8A8_SINT",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_COMPRESSED_SRGB8_ETC2": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadETC2SRGB8ToRGBA8",
- "dxgiFormat": "DXGI_FORMAT_R8G8B8A8_UNORM_SRGB",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_DEPTH32F_STENCIL8": {
- "GL_FLOAT_32_UNSIGNED_INT_24_8_REV": [
- {
- "loadFunction": "LoadToNative<GLuint,2>",
- "dxgiFormat": "DXGI_FORMAT_R32G8X24_TYPELESS",
- "requiresConversion": "false"
- },
- {
- "loadFunction": "UnimplementedLoadFunction",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_RG8I": {
- "GL_BYTE": [
- {
- "loadFunction": "LoadToNative<GLbyte,2>",
- "dxgiFormat": "DXGI_FORMAT_R8G8_SINT",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_R32UI": {
- "GL_UNSIGNED_INT": [
- {
- "loadFunction": "LoadToNative<GLuint,1>",
- "dxgiFormat": "DXGI_FORMAT_R32_UINT",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_BGR5_A1_ANGLEX": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadToNative<GLubyte,4>",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "false"
- }
- ],
- "GL_UNSIGNED_SHORT_1_5_5_5_REV_EXT": [
- {
- "loadFunction": "LoadRGB5A1ToRGBA8",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_COMPRESSED_RG11_EAC": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadEACRG11ToRG8",
- "dxgiFormat": "DXGI_FORMAT_R8G8_UNORM",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_SRGB8_ALPHA8": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadToNative<GLubyte,4>",
- "dxgiFormat": "DXGI_FORMAT_R8G8B8A8_UNORM_SRGB",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_LUMINANCE_ALPHA16F_EXT": {
- "GL_HALF_FLOAT": [
- {
- "loadFunction": "LoadLA16FToRGBA16F",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ],
- "GL_HALF_FLOAT_OES": [
- {
- "loadFunction": "LoadLA16FToRGBA16F",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_RGBA": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "UnreachableLoadFunction",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ],
- "GL_UNSIGNED_SHORT_4_4_4_4": [
- {
- "loadFunction": "UnreachableLoadFunction",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ],
- "GL_UNSIGNED_SHORT_5_5_5_1": [
- {
- "loadFunction": "UnreachableLoadFunction",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_DEPTH24_STENCIL8": {
- "GL_UNSIGNED_INT_24_8": [
- {
- "loadFunction": "LoadR32ToR24G8",
- "dxgiFormat": "DXGI_FORMAT_R24G8_TYPELESS",
- "requiresConversion": "true"
- },
- {
- "loadFunction": "LoadR32ToR24G8",
- "dxgiFormat": "DXGI_FORMAT_D24_UNORM_S8_UINT",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_RGB16I": {
- "GL_SHORT": [
- {
- "loadFunction": "LoadToNative3To4<GLshort,0x0001>",
- "dxgiFormat": "DXGI_FORMAT_R16G16B16A16_SINT",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_R8UI": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadToNative<GLubyte,1>",
- "dxgiFormat": "DXGI_FORMAT_R8_UINT",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_ALPHA": {
- "GL_HALF_FLOAT": [
- {
- "loadFunction": "LoadA16FToRGBA16F",
- "dxgiFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT",
- "requiresConversion": "true"
- }
- ],
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "UnreachableLoadFunction",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ],
- "GL_FLOAT": [
- {
- "loadFunction": "LoadA32FToRGBA32F",
- "dxgiFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT",
- "requiresConversion": "true"
- }
- ],
- "GL_HALF_FLOAT_OES": [
- {
- "loadFunction": "LoadA16FToRGBA16F",
- "dxgiFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_RGB16F": {
- "GL_HALF_FLOAT": [
- {
- "loadFunction": "LoadToNative3To4<GLhalf,gl::Float16One>",
- "dxgiFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT",
- "requiresConversion": "true"
- }
- ],
- "GL_FLOAT": [
- {
- "loadFunction": "LoadRGB32FToRGBA16F",
- "dxgiFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT",
- "requiresConversion": "true"
- }
- ],
- "GL_HALF_FLOAT_OES": [
- {
- "loadFunction": "LoadToNative3To4<GLhalf,gl::Float16One>",
- "dxgiFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_COMPRESSED_SIGNED_R11_EAC": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadEACR11SToR8",
- "dxgiFormat": "DXGI_FORMAT_R8_SNORM",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_COMPRESSED_RGB_S3TC_DXT1_EXT": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadCompressedToNative<4,4,8>",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_COMPRESSED_RGBA_S3TC_DXT1_EXT": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadCompressedToNative<4,4,8>",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_STENCIL_INDEX8": {
- "DXGI_FORMAT_R24G8_TYPELESS": [
- {
- "loadFunction": "UnimplementedLoadFunction",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ],
- "DXGI_FORMAT_D24_UNORM_S8_UINT": [
- {
- "loadFunction": "UnimplementedLoadFunction",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_LUMINANCE_ALPHA32F_EXT": {
- "GL_FLOAT": [
- {
- "loadFunction": "LoadLA32FToRGBA32F",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_RGB8UI": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadToNative3To4<GLubyte,0x01>",
- "dxgiFormat": "DXGI_FORMAT_R8G8B8A8_UINT",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_DEPTH_COMPONENT24": {
- "GL_UNSIGNED_INT": [
- {
- "loadFunction": "LoadR32ToR24G8",
- "dxgiFormat": "DXGI_FORMAT_R24G8_TYPELESS",
- "requiresConversion": "true"
- },
- {
- "loadFunction": "LoadR32ToR24G8",
- "dxgiFormat": "DXGI_FORMAT_D24_UNORM_S8_UINT",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_R32I": {
- "GL_INT": [
- {
- "loadFunction": "LoadToNative<GLint,1>",
- "dxgiFormat": "DXGI_FORMAT_R32_SINT",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_DEPTH_COMPONENT32_OES": {
- "GL_UNSIGNED_INT": [
- {
- "loadFunction": "LoadR32ToR24G8",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_R32F": {
- "GL_FLOAT": [
- {
- "loadFunction": "LoadToNative<GLfloat,1>",
- "dxgiFormat": "DXGI_FORMAT_R32_FLOAT",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_RG16F": {
- "GL_HALF_FLOAT": [
- {
- "loadFunction": "LoadToNative<GLhalf,2>",
- "dxgiFormat": "DXGI_FORMAT_R16G16_FLOAT",
- "requiresConversion": "false"
- }
- ],
- "GL_FLOAT": [
- {
- "loadFunction": "Load32FTo16F<2>",
- "dxgiFormat": "DXGI_FORMAT_R16G16_FLOAT",
- "requiresConversion": "true"
- }
- ],
- "GL_HALF_FLOAT_OES": [
- {
- "loadFunction": "LoadToNative<GLhalf,2>",
- "dxgiFormat": "DXGI_FORMAT_R16G16_FLOAT",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_RGB565": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadToNative3To4<GLubyte,0xFF>",
- "dxgiFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "requiresConversion": "true"
- }
- ],
- "GL_UNSIGNED_SHORT_5_6_5": [
- {
- "loadFunction": "LoadR5G6B5ToRGBA8",
- "dxgiFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "requiresConversion": "true"
- },
- {
- "loadFunction": "LoadToNative<GLushort,1>",
- "dxgiFormat": "DXGI_FORMAT_B5G6R5_UNORM",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_LUMINANCE16F_EXT": {
- "GL_HALF_FLOAT": [
- {
- "loadFunction": "LoadL16FToRGBA16F",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ],
- "GL_HALF_FLOAT_OES": [
- {
- "loadFunction": "LoadL16FToRGBA16F",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_RG16UI": {
- "GL_UNSIGNED_SHORT": [
- {
- "loadFunction": "LoadToNative<GLushort,2>",
- "dxgiFormat": "DXGI_FORMAT_R16G16_UINT",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_COMPRESSED_RGBA_S3TC_DXT3_ANGLE": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadCompressedToNative<4,4,16>",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_RG16I": {
- "GL_SHORT": [
- {
- "loadFunction": "LoadToNative<GLshort,2>",
- "dxgiFormat": "DXGI_FORMAT_R16G16_SINT",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_BGRA8_EXT": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadToNative<GLubyte,4>",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_ALPHA16F_EXT": {
- "GL_HALF_FLOAT": [
- {
- "loadFunction": "LoadA16FToRGBA16F",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ],
- "GL_HALF_FLOAT_OES": [
- {
- "loadFunction": "LoadA16FToRGBA16F",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_RGBA4": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadToNative<GLubyte,4>",
- "dxgiFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "requiresConversion": "false"
- }
- ],
- "GL_UNSIGNED_SHORT_4_4_4_4": [
- {
- "loadFunction": "LoadRGBA4ToRGBA8",
- "dxgiFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "requiresConversion": "true"
- },
- {
- "loadFunction": "LoadRGBA4ToARGB4",
- "dxgiFormat": "DXGI_FORMAT_B4G4R4A4_UNORM",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_RGBA8": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadToNative<GLubyte,4>",
- "dxgiFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_LUMINANCE": {
- "GL_HALF_FLOAT": [
- {
- "loadFunction": "LoadL16FToRGBA16F",
- "dxgiFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT",
- "requiresConversion": "true"
- }
- ],
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "UnreachableLoadFunction",
- "dxgiFormat": "DXGI_FORMAT_UNKNOWN",
- "requiresConversion": "true"
- }
- ],
- "GL_FLOAT": [
- {
- "loadFunction": "LoadL32FToRGBA32F",
- "dxgiFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT",
- "requiresConversion": "true"
- }
- ],
- "GL_HALF_FLOAT_OES": [
- {
- "loadFunction": "LoadL16FToRGBA16F",
- "dxgiFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_RGB10_A2UI": {
- "GL_UNSIGNED_INT_2_10_10_10_REV": [
- {
- "loadFunction": "LoadToNative<GLuint,1>",
- "dxgiFormat": "DXGI_FORMAT_R10G10B10A2_UINT",
- "requiresConversion": "false"
- }
- ]
- },
- "GL_ETC1_RGB8_OES": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadETC1RGB8ToRGBA8",
- "dxgiFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "requiresConversion": "true"
- }
- ]
- },
- "GL_ETC1_RGB8_LOSSY_DECODE_ANGLE": {
- "GL_UNSIGNED_BYTE": [
- {
- "loadFunction": "LoadETC1RGB8ToBC1",
- "dxgiFormat": "DXGI_FORMAT_BC1_UNORM",
- "requiresConversion": "true"
- }
- ]
- }
-} \ No newline at end of file
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/load_functions_table.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/load_functions_table.h
deleted file mode 100644
index b17062f68d..0000000000
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/load_functions_table.h
+++ /dev/null
@@ -1,31 +0,0 @@
-//
-// Copyright 2015 The ANGLE Project Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-//
-// load_functions_table:
-// Contains load functions table depending on internal format and dxgi format
-//
-
-#ifndef LIBANGLE_RENDERER_D3D_D3D11_LOADFUNCTIONSTABLE_H_
-#define LIBANGLE_RENDERER_D3D_D3D11_LOADFUNCTIONSTABLE_H_
-
-#include <map>
-
-#include "libANGLE/renderer/d3d/d3d11/Renderer11.h"
-#include "libANGLE/renderer/d3d/d3d11/texture_format_table.h"
-
-namespace rx
-{
-
-namespace d3d11
-{
-
-const std::map<GLenum, LoadImageFunctionInfo> &GetLoadFunctionsMap(GLenum internalFormat,
- DXGI_FORMAT dxgiFormat);
-
-} // namespace d3d11
-
-} // namespace rx
-
-#endif // LIBANGLE_RENDERER_D3D_D3D11_LOADFUNCTIONSTABLE_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/load_functions_table_autogen.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/load_functions_table_autogen.cpp
deleted file mode 100644
index acb48b9573..0000000000
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/load_functions_table_autogen.cpp
+++ /dev/null
@@ -1,2098 +0,0 @@
-// GENERATED FILE - DO NOT EDIT.
-// Generated by gen_load_functions_table.py using data from load_functions_data.json
-//
-// Copyright 2015 The ANGLE Project Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-//
-// load_functions_table:
-// Contains the GetLoadFunctionsMap for texture_format_util.h
-//
-
-#include "libANGLE/renderer/d3d/d3d11/load_functions_table.h"
-#include "libANGLE/renderer/d3d/d3d11/formatutils11.h"
-#include "libANGLE/renderer/d3d/d3d11/texture_format_table.h"
-#include "libANGLE/renderer/d3d/loadimage.h"
-#include "libANGLE/renderer/d3d/loadimage_etc.h"
-
-namespace rx
-{
-
-namespace d3d11
-{
-
-namespace
-{
-
-// ES3 image loading functions vary based on:
-// - the GL internal format (supplied to glTex*Image*D)
-// - the GL data type given (supplied to glTex*Image*D)
-// - the target DXGI_FORMAT that the image will be loaded into (which is chosen based on the D3D
-// device's capabilities)
-// This map type determines which loading function to use, based on these three parameters.
-// Source formats and types are taken from Tables 3.2 and 3.3 of the ES 3 spec.
-void UnimplementedLoadFunction(size_t width,
- size_t height,
- size_t depth,
- const uint8_t *input,
- size_t inputRowPitch,
- size_t inputDepthPitch,
- uint8_t *output,
- size_t outputRowPitch,
- size_t outputDepthPitch)
-{
- UNIMPLEMENTED();
-}
-
-void UnreachableLoadFunction(size_t width,
- size_t height,
- size_t depth,
- const uint8_t *input,
- size_t inputRowPitch,
- size_t inputDepthPitch,
- uint8_t *output,
- size_t outputRowPitch,
- size_t outputDepthPitch)
-{
- UNREACHABLE();
-}
-
-} // namespace
-
-// TODO we can replace these maps with more generated code
-const std::map<GLenum, LoadImageFunctionInfo> &GetLoadFunctionsMap(GLenum internalFormat,
- DXGI_FORMAT dxgiFormat)
-{
- // clang-format off
- switch (internalFormat)
- {
- case GL_ALPHA:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R16G16B16A16_FLOAT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_HALF_FLOAT] = LoadImageFunctionInfo(LoadA16FToRGBA16F, true);
- loadMap[GL_HALF_FLOAT_OES] = LoadImageFunctionInfo(LoadA16FToRGBA16F, true);
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(UnreachableLoadFunction, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- case DXGI_FORMAT_R32G32B32A32_FLOAT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_FLOAT] = LoadImageFunctionInfo(LoadA32FToRGBA32F, true);
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(UnreachableLoadFunction, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- case DXGI_FORMAT_UNKNOWN:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(UnreachableLoadFunction, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(UnreachableLoadFunction, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- }
- }
- case GL_ALPHA16F_EXT:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_UNKNOWN:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_HALF_FLOAT] = LoadImageFunctionInfo(LoadA16FToRGBA16F, true);
- loadMap[GL_HALF_FLOAT_OES] = LoadImageFunctionInfo(LoadA16FToRGBA16F, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_HALF_FLOAT] = LoadImageFunctionInfo(LoadA16FToRGBA16F, true);
- loadMap[GL_HALF_FLOAT_OES] = LoadImageFunctionInfo(LoadA16FToRGBA16F, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- }
- }
- case GL_ALPHA32F_EXT:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_UNKNOWN:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_FLOAT] = LoadImageFunctionInfo(LoadA32FToRGBA32F, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_FLOAT] = LoadImageFunctionInfo(LoadA32FToRGBA32F, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- }
- }
- case GL_ALPHA8_EXT:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_A8_UNORM:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadToNative<GLubyte,1>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- case DXGI_FORMAT_R8G8B8A8_UNORM:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadA8ToRGBA8, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_BGR5_A1_ANGLEX:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_UNKNOWN:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_SHORT_1_5_5_5_REV_EXT] = LoadImageFunctionInfo(LoadRGB5A1ToRGBA8, true);
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadToNative<GLubyte,4>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadToNative<GLubyte,4>, true);
- loadMap[GL_UNSIGNED_SHORT_1_5_5_5_REV_EXT] = LoadImageFunctionInfo(LoadRGB5A1ToRGBA8, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- }
- }
- case GL_BGRA4_ANGLEX:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_UNKNOWN:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_SHORT_4_4_4_4_REV_EXT] = LoadImageFunctionInfo(LoadRGBA4ToRGBA8, true);
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadToNative<GLubyte,4>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadToNative<GLubyte,4>, true);
- loadMap[GL_UNSIGNED_SHORT_4_4_4_4_REV_EXT] = LoadImageFunctionInfo(LoadRGBA4ToRGBA8, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- }
- }
- case GL_BGRA8_EXT:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_UNKNOWN:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadToNative<GLubyte,4>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadToNative<GLubyte,4>, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- }
- }
- case GL_BGRA_EXT:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_UNKNOWN:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(UnreachableLoadFunction, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(UnreachableLoadFunction, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- }
- }
- case GL_COMPRESSED_R11_EAC:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8_UNORM:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadEACR11ToR8, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_COMPRESSED_RG11_EAC:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8G8_UNORM:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadEACRG11ToRG8, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_COMPRESSED_RGB8_ETC2:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8G8B8A8_UNORM:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadETC2RGB8ToRGBA8, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_COMPRESSED_RGB8_PUNCHTHROUGH_ALPHA1_ETC2:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8G8B8A8_UNORM:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadETC2RGB8A1ToRGBA8, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_COMPRESSED_RGBA8_ETC2_EAC:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8G8B8A8_UNORM:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadETC2RGBA8ToRGBA8, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_COMPRESSED_RGBA_S3TC_DXT1_EXT:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_UNKNOWN:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadCompressedToNative<4,4,8>, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadCompressedToNative<4,4,8>, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- }
- }
- case GL_COMPRESSED_RGBA_S3TC_DXT3_ANGLE:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_UNKNOWN:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadCompressedToNative<4,4,16>, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadCompressedToNative<4,4,16>, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- }
- }
- case GL_COMPRESSED_RGBA_S3TC_DXT5_ANGLE:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_UNKNOWN:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadCompressedToNative<4,4,16>, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadCompressedToNative<4,4,16>, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- }
- }
- case GL_COMPRESSED_RGB_S3TC_DXT1_EXT:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_UNKNOWN:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadCompressedToNative<4,4,8>, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadCompressedToNative<4,4,8>, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- }
- }
- case GL_COMPRESSED_SIGNED_R11_EAC:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8_SNORM:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadEACR11SToR8, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_COMPRESSED_SIGNED_RG11_EAC:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8G8_SNORM:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadEACRG11SToRG8, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_COMPRESSED_SRGB8_ALPHA8_ETC2_EAC:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadETC2SRGBA8ToSRGBA8, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_COMPRESSED_SRGB8_ETC2:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadETC2SRGB8ToRGBA8, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_COMPRESSED_SRGB8_PUNCHTHROUGH_ALPHA1_ETC2:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadETC2SRGB8A1ToRGBA8, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_DEPTH24_STENCIL8:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_D24_UNORM_S8_UINT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_INT_24_8] = LoadImageFunctionInfo(LoadR32ToR24G8, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- case DXGI_FORMAT_R24G8_TYPELESS:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_INT_24_8] = LoadImageFunctionInfo(LoadR32ToR24G8, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_DEPTH32F_STENCIL8:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R32G8X24_TYPELESS:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_FLOAT_32_UNSIGNED_INT_24_8_REV] = LoadImageFunctionInfo(LoadToNative<GLuint,2>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- case DXGI_FORMAT_UNKNOWN:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_FLOAT_32_UNSIGNED_INT_24_8_REV] = LoadImageFunctionInfo(UnimplementedLoadFunction, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_FLOAT_32_UNSIGNED_INT_24_8_REV] = LoadImageFunctionInfo(UnimplementedLoadFunction, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- }
- }
- case GL_DEPTH_COMPONENT16:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_D16_UNORM:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_SHORT] = LoadImageFunctionInfo(LoadToNative<GLushort,1>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- case DXGI_FORMAT_R16_TYPELESS:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_INT] = LoadImageFunctionInfo(LoadR32ToR16, true);
- loadMap[GL_UNSIGNED_SHORT] = LoadImageFunctionInfo(LoadToNative<GLushort,1>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_DEPTH_COMPONENT24:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_D24_UNORM_S8_UINT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_INT] = LoadImageFunctionInfo(LoadR32ToR24G8, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- case DXGI_FORMAT_R24G8_TYPELESS:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_INT] = LoadImageFunctionInfo(LoadR32ToR24G8, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_DEPTH_COMPONENT32F:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R32_TYPELESS:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_FLOAT] = LoadImageFunctionInfo(LoadToNative<GLfloat,1>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- case DXGI_FORMAT_UNKNOWN:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_FLOAT] = LoadImageFunctionInfo(UnimplementedLoadFunction, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_FLOAT] = LoadImageFunctionInfo(UnimplementedLoadFunction, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- }
- }
- case GL_DEPTH_COMPONENT32_OES:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_UNKNOWN:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_INT] = LoadImageFunctionInfo(LoadR32ToR24G8, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_INT] = LoadImageFunctionInfo(LoadR32ToR24G8, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- }
- }
- case GL_ETC1_RGB8_LOSSY_DECODE_ANGLE:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_BC1_UNORM:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadETC1RGB8ToBC1, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_ETC1_RGB8_OES:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8G8B8A8_UNORM:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadETC1RGB8ToRGBA8, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_LUMINANCE:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R16G16B16A16_FLOAT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_HALF_FLOAT] = LoadImageFunctionInfo(LoadL16FToRGBA16F, true);
- loadMap[GL_HALF_FLOAT_OES] = LoadImageFunctionInfo(LoadL16FToRGBA16F, true);
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(UnreachableLoadFunction, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- case DXGI_FORMAT_R32G32B32A32_FLOAT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_FLOAT] = LoadImageFunctionInfo(LoadL32FToRGBA32F, true);
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(UnreachableLoadFunction, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- case DXGI_FORMAT_UNKNOWN:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(UnreachableLoadFunction, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(UnreachableLoadFunction, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- }
- }
- case GL_LUMINANCE16F_EXT:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_UNKNOWN:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_HALF_FLOAT] = LoadImageFunctionInfo(LoadL16FToRGBA16F, true);
- loadMap[GL_HALF_FLOAT_OES] = LoadImageFunctionInfo(LoadL16FToRGBA16F, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_HALF_FLOAT] = LoadImageFunctionInfo(LoadL16FToRGBA16F, true);
- loadMap[GL_HALF_FLOAT_OES] = LoadImageFunctionInfo(LoadL16FToRGBA16F, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- }
- }
- case GL_LUMINANCE32F_EXT:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_UNKNOWN:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_FLOAT] = LoadImageFunctionInfo(LoadL32FToRGBA32F, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_FLOAT] = LoadImageFunctionInfo(LoadL32FToRGBA32F, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- }
- }
- case GL_LUMINANCE8_ALPHA8_EXT:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_UNKNOWN:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadLA8ToRGBA8, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadLA8ToRGBA8, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- }
- }
- case GL_LUMINANCE8_EXT:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_UNKNOWN:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadL8ToRGBA8, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadL8ToRGBA8, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- }
- }
- case GL_LUMINANCE_ALPHA:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R16G16B16A16_FLOAT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_HALF_FLOAT] = LoadImageFunctionInfo(LoadLA16FToRGBA16F, true);
- loadMap[GL_HALF_FLOAT_OES] = LoadImageFunctionInfo(LoadLA16FToRGBA16F, true);
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(UnreachableLoadFunction, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- case DXGI_FORMAT_R32G32B32A32_FLOAT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_FLOAT] = LoadImageFunctionInfo(LoadLA32FToRGBA32F, true);
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(UnreachableLoadFunction, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- case DXGI_FORMAT_UNKNOWN:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(UnreachableLoadFunction, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(UnreachableLoadFunction, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- }
- }
- case GL_LUMINANCE_ALPHA16F_EXT:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_UNKNOWN:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_HALF_FLOAT] = LoadImageFunctionInfo(LoadLA16FToRGBA16F, true);
- loadMap[GL_HALF_FLOAT_OES] = LoadImageFunctionInfo(LoadLA16FToRGBA16F, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_HALF_FLOAT] = LoadImageFunctionInfo(LoadLA16FToRGBA16F, true);
- loadMap[GL_HALF_FLOAT_OES] = LoadImageFunctionInfo(LoadLA16FToRGBA16F, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- }
- }
- case GL_LUMINANCE_ALPHA32F_EXT:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_UNKNOWN:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_FLOAT] = LoadImageFunctionInfo(LoadLA32FToRGBA32F, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_FLOAT] = LoadImageFunctionInfo(LoadLA32FToRGBA32F, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- }
- }
- case GL_R11F_G11F_B10F:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R11G11B10_FLOAT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_HALF_FLOAT] = LoadImageFunctionInfo(LoadRGB16FToRG11B10F, true);
- loadMap[GL_HALF_FLOAT_OES] = LoadImageFunctionInfo(LoadRGB16FToRG11B10F, true);
- loadMap[GL_FLOAT] = LoadImageFunctionInfo(LoadRGB32FToRG11B10F, true);
- loadMap[GL_UNSIGNED_INT_10F_11F_11F_REV] = LoadImageFunctionInfo(LoadToNative<GLuint,1>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_R16F:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R16_FLOAT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_FLOAT] = LoadImageFunctionInfo(Load32FTo16F<1>, true);
- loadMap[GL_HALF_FLOAT] = LoadImageFunctionInfo(LoadToNative<GLhalf,1>, false);
- loadMap[GL_HALF_FLOAT_OES] = LoadImageFunctionInfo(LoadToNative<GLhalf,1>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_R16I:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R16_SINT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_SHORT] = LoadImageFunctionInfo(LoadToNative<GLshort,1>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_R16UI:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R16_UINT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_SHORT] = LoadImageFunctionInfo(LoadToNative<GLushort,1>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_R32F:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R32_FLOAT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_FLOAT] = LoadImageFunctionInfo(LoadToNative<GLfloat,1>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_R32I:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R32_SINT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_INT] = LoadImageFunctionInfo(LoadToNative<GLint,1>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_R32UI:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R32_UINT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_INT] = LoadImageFunctionInfo(LoadToNative<GLuint,1>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_R8:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8_UNORM:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadToNative<GLubyte,1>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_R8I:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8_SINT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_BYTE] = LoadImageFunctionInfo(LoadToNative<GLbyte,1>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_R8UI:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8_UINT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadToNative<GLubyte,1>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_R8_SNORM:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8_SNORM:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_BYTE] = LoadImageFunctionInfo(LoadToNative<GLbyte,1>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RG16F:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R16G16_FLOAT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_FLOAT] = LoadImageFunctionInfo(Load32FTo16F<2>, true);
- loadMap[GL_HALF_FLOAT] = LoadImageFunctionInfo(LoadToNative<GLhalf,2>, false);
- loadMap[GL_HALF_FLOAT_OES] = LoadImageFunctionInfo(LoadToNative<GLhalf,2>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RG16I:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R16G16_SINT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_SHORT] = LoadImageFunctionInfo(LoadToNative<GLshort,2>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RG16UI:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R16G16_UINT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_SHORT] = LoadImageFunctionInfo(LoadToNative<GLushort,2>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RG32F:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R32G32_FLOAT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_FLOAT] = LoadImageFunctionInfo(LoadToNative<GLfloat,2>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RG32I:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R32G32_SINT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_INT] = LoadImageFunctionInfo(LoadToNative<GLint,2>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RG32UI:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R32G32_UINT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_INT] = LoadImageFunctionInfo(LoadToNative<GLuint,2>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RG8:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8G8_UNORM:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadToNative<GLubyte,2>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RG8I:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8G8_SINT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_BYTE] = LoadImageFunctionInfo(LoadToNative<GLbyte,2>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RG8UI:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8G8_UINT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadToNative<GLubyte,2>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RG8_SNORM:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8G8_SNORM:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_BYTE] = LoadImageFunctionInfo(LoadToNative<GLbyte,2>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RGB:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_UNKNOWN:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(UnreachableLoadFunction, true);
- loadMap[GL_UNSIGNED_SHORT_5_6_5] = LoadImageFunctionInfo(UnreachableLoadFunction, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(UnreachableLoadFunction, true);
- loadMap[GL_UNSIGNED_SHORT_5_6_5] = LoadImageFunctionInfo(UnreachableLoadFunction, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- }
- }
- case GL_RGB10_A2:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R10G10B10A2_UNORM:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_INT_2_10_10_10_REV] = LoadImageFunctionInfo(LoadToNative<GLuint,1>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RGB10_A2UI:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R10G10B10A2_UINT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_INT_2_10_10_10_REV] = LoadImageFunctionInfo(LoadToNative<GLuint,1>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RGB16F:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R16G16B16A16_FLOAT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_FLOAT] = LoadImageFunctionInfo(LoadRGB32FToRGBA16F, true);
- loadMap[GL_HALF_FLOAT] = LoadImageFunctionInfo(LoadToNative3To4<GLhalf,gl::Float16One>, true);
- loadMap[GL_HALF_FLOAT_OES] = LoadImageFunctionInfo(LoadToNative3To4<GLhalf,gl::Float16One>, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RGB16I:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R16G16B16A16_SINT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_SHORT] = LoadImageFunctionInfo(LoadToNative3To4<GLshort,0x0001>, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RGB16UI:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R16G16B16A16_UINT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_SHORT] = LoadImageFunctionInfo(LoadToNative3To4<GLushort,0x0001>, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RGB32F:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R32G32B32A32_FLOAT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_FLOAT] = LoadImageFunctionInfo(LoadToNative3To4<GLfloat,gl::Float32One>, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RGB32I:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R32G32B32A32_SINT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_INT] = LoadImageFunctionInfo(LoadToNative3To4<GLint,0x00000001>, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RGB32UI:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R32G32B32A32_UINT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_INT] = LoadImageFunctionInfo(LoadToNative3To4<GLuint,0x00000001>, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RGB565:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_B5G6R5_UNORM:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_SHORT_5_6_5] = LoadImageFunctionInfo(LoadToNative<GLushort,1>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- case DXGI_FORMAT_R8G8B8A8_UNORM:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_SHORT_5_6_5] = LoadImageFunctionInfo(LoadR5G6B5ToRGBA8, true);
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadToNative3To4<GLubyte,0xFF>, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RGB5_A1:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_B5G5R5A1_UNORM:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_SHORT_5_5_5_1] = LoadImageFunctionInfo(LoadRGB5A1ToA1RGB5, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- case DXGI_FORMAT_R8G8B8A8_UNORM:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_INT_2_10_10_10_REV] = LoadImageFunctionInfo(LoadRGB10A2ToRGBA8, true);
- loadMap[GL_UNSIGNED_SHORT_5_5_5_1] = LoadImageFunctionInfo(LoadRGB5A1ToRGBA8, true);
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadToNative<GLubyte,4>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RGB8:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8G8B8A8_UNORM:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadToNative3To4<GLubyte,0xFF>, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RGB8I:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8G8B8A8_SINT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_BYTE] = LoadImageFunctionInfo(LoadToNative3To4<GLbyte,0x01>, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RGB8UI:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8G8B8A8_UINT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadToNative3To4<GLubyte,0x01>, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RGB8_SNORM:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8G8B8A8_SNORM:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_BYTE] = LoadImageFunctionInfo(LoadToNative3To4<GLbyte,0x7F>, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RGB9_E5:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R9G9B9E5_SHAREDEXP:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_HALF_FLOAT] = LoadImageFunctionInfo(LoadRGB16FToRGB9E5, true);
- loadMap[GL_HALF_FLOAT_OES] = LoadImageFunctionInfo(LoadRGB16FToRGB9E5, true);
- loadMap[GL_FLOAT] = LoadImageFunctionInfo(LoadRGB32FToRGB9E5, true);
- loadMap[GL_UNSIGNED_INT_5_9_9_9_REV] = LoadImageFunctionInfo(LoadToNative<GLuint,1>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RGBA:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_UNKNOWN:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(UnreachableLoadFunction, true);
- loadMap[GL_UNSIGNED_SHORT_4_4_4_4] = LoadImageFunctionInfo(UnreachableLoadFunction, true);
- loadMap[GL_UNSIGNED_SHORT_5_5_5_1] = LoadImageFunctionInfo(UnreachableLoadFunction, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(UnreachableLoadFunction, true);
- loadMap[GL_UNSIGNED_SHORT_4_4_4_4] = LoadImageFunctionInfo(UnreachableLoadFunction, true);
- loadMap[GL_UNSIGNED_SHORT_5_5_5_1] = LoadImageFunctionInfo(UnreachableLoadFunction, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- }
- }
- case GL_RGBA16F:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R16G16B16A16_FLOAT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_FLOAT] = LoadImageFunctionInfo(Load32FTo16F<4>, true);
- loadMap[GL_HALF_FLOAT] = LoadImageFunctionInfo(LoadToNative<GLhalf,4>, false);
- loadMap[GL_HALF_FLOAT_OES] = LoadImageFunctionInfo(LoadToNative<GLhalf,4>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RGBA16I:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R16G16B16A16_SINT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_SHORT] = LoadImageFunctionInfo(LoadToNative<GLshort,4>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RGBA16UI:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R16G16B16A16_UINT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_SHORT] = LoadImageFunctionInfo(LoadToNative<GLushort,4>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RGBA32F:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R32G32B32A32_FLOAT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_FLOAT] = LoadImageFunctionInfo(LoadToNative<GLfloat,4>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RGBA32I:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R32G32B32A32_SINT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_INT] = LoadImageFunctionInfo(LoadToNative<GLint,4>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RGBA32UI:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R32G32B32A32_UINT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_INT] = LoadImageFunctionInfo(LoadToNative<GLuint,4>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RGBA4:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_B4G4R4A4_UNORM:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_SHORT_4_4_4_4] = LoadImageFunctionInfo(LoadRGBA4ToARGB4, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- case DXGI_FORMAT_R8G8B8A8_UNORM:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_SHORT_4_4_4_4] = LoadImageFunctionInfo(LoadRGBA4ToRGBA8, true);
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadToNative<GLubyte,4>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RGBA8:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8G8B8A8_UNORM:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadToNative<GLubyte,4>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RGBA8I:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8G8B8A8_SINT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_BYTE] = LoadImageFunctionInfo(LoadToNative<GLbyte,4>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RGBA8UI:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8G8B8A8_UINT:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadToNative<GLubyte,4>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_RGBA8_SNORM:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8G8B8A8_SNORM:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_BYTE] = LoadImageFunctionInfo(LoadToNative<GLbyte,4>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_SRGB8:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadToNative3To4<GLubyte,0xFF>, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_SRGB8_ALPHA8:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[GL_UNSIGNED_BYTE] = LoadImageFunctionInfo(LoadToNative<GLubyte,4>, false);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- break;
- }
- }
- case GL_STENCIL_INDEX8:
- {
- switch (dxgiFormat)
- {
- case DXGI_FORMAT_UNKNOWN:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[DXGI_FORMAT_D24_UNORM_S8_UINT] = LoadImageFunctionInfo(UnimplementedLoadFunction, true);
- loadMap[DXGI_FORMAT_R24G8_TYPELESS] = LoadImageFunctionInfo(UnimplementedLoadFunction, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- default:
- {
- static const std::map<GLenum, LoadImageFunctionInfo> loadFunctionsMap = []() {
- std::map<GLenum, LoadImageFunctionInfo> loadMap;
- loadMap[DXGI_FORMAT_D24_UNORM_S8_UINT] = LoadImageFunctionInfo(UnimplementedLoadFunction, true);
- loadMap[DXGI_FORMAT_R24G8_TYPELESS] = LoadImageFunctionInfo(UnimplementedLoadFunction, true);
- return loadMap;
- }();
-
- return loadFunctionsMap;
- }
- }
- }
-
- default:
- {
- static std::map<GLenum, LoadImageFunctionInfo> emptyLoadFunctionsMap;
- return emptyLoadFunctionsMap;
- }
- }
- // clang-format on
-
-} // GetLoadFunctionsMap
-
-} // namespace d3d11
-
-} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/renderer11_utils.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/renderer11_utils.cpp
index a1175db9af..d059b36120 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/renderer11_utils.cpp
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/renderer11_utils.cpp
@@ -12,319 +12,52 @@
#include <algorithm>
#include "common/debug.h"
-#include "libANGLE/formatutils.h"
+#include "libANGLE/Buffer.h"
+#include "libANGLE/Context.h"
#include "libANGLE/Framebuffer.h"
#include "libANGLE/Program.h"
+#include "libANGLE/State.h"
+#include "libANGLE/VertexArray.h"
+#include "libANGLE/formatutils.h"
+#include "libANGLE/renderer/d3d/BufferD3D.h"
+#include "libANGLE/renderer/d3d/FramebufferD3D.h"
+#include "libANGLE/renderer/d3d/IndexBuffer.h"
+#include "libANGLE/renderer/d3d/d3d11/RenderTarget11.h"
+#include "libANGLE/renderer/d3d/d3d11/Renderer11.h"
#include "libANGLE/renderer/d3d/d3d11/dxgi_support_table.h"
#include "libANGLE/renderer/d3d/d3d11/formatutils11.h"
-#include "libANGLE/renderer/d3d/d3d11/Renderer11.h"
-#include "libANGLE/renderer/d3d/d3d11/RenderTarget11.h"
#include "libANGLE/renderer/d3d/d3d11/texture_format_table.h"
-#include "libANGLE/renderer/d3d/FramebufferD3D.h"
-#include "libANGLE/renderer/d3d/WorkaroundsD3D.h"
-
-#ifndef D3D_FL9_1_DEFAULT_MAX_ANISOTROPY
-# define D3D_FL9_1_DEFAULT_MAX_ANISOTROPY 2
-#endif
-#ifndef D3D_FL9_1_SIMULTANEOUS_RENDER_TARGET_COUNT
-# define D3D_FL9_1_SIMULTANEOUS_RENDER_TARGET_COUNT 1
-#endif
-#ifndef D3D_FL9_3_SIMULTANEOUS_RENDER_TARGET_COUNT
-# define D3D_FL9_3_SIMULTANEOUS_RENDER_TARGET_COUNT 4
-#endif
-#ifndef D3D_FL9_1_IA_PRIMITIVE_MAX_COUNT
-# define D3D_FL9_1_IA_PRIMITIVE_MAX_COUNT 65535
-#endif
-#ifndef D3D_FL9_2_IA_PRIMITIVE_MAX_COUNT
-# define D3D_FL9_2_IA_PRIMITIVE_MAX_COUNT 1048575
-#endif
-#ifndef D3D_FL9_1_REQ_TEXTURECUBE_DIMENSION
-# define D3D_FL9_1_REQ_TEXTURECUBE_DIMENSION 512
-#endif
-#ifndef D3D_FL9_3_REQ_TEXTURECUBE_DIMENSION
-# define D3D_FL9_3_REQ_TEXTURECUBE_DIMENSION 4096
-#endif
-#ifndef D3D_FL9_1_REQ_TEXTURE2D_U_OR_V_DIMENSION
-# define D3D_FL9_1_REQ_TEXTURE2D_U_OR_V_DIMENSION 2048
-#endif
-#ifndef D3D_FL9_1_REQ_TEXTURE3D_U_V_OR_W_DIMENSION
-# define D3D_FL9_1_REQ_TEXTURE3D_U_V_OR_W_DIMENSION 256
-#endif
-#ifndef D3D_FL9_3_REQ_TEXTURE2D_U_OR_V_DIMENSION
-# define D3D_FL9_3_REQ_TEXTURE2D_U_OR_V_DIMENSION 4096
-#endif
-#ifndef D3D11_REQ_TEXTURECUBE_DIMENSION
-# define D3D11_REQ_TEXTURECUBE_DIMENSION 16384
-#endif
-#ifndef D3D11_REQ_TEXTURE2D_ARRAY_AXIS_DIMENSION
-# define D3D11_REQ_TEXTURE2D_ARRAY_AXIS_DIMENSION 2048
-#endif
-#ifndef D3D11_REQ_TEXTURE3D_U_V_OR_W_DIMENSION
-# define D3D11_REQ_TEXTURE3D_U_V_OR_W_DIMENSION 2048
-#endif
-#ifndef D3D11_REQ_DRAWINDEXED_INDEX_COUNT_2_TO_EXP
-# define D3D11_REQ_DRAWINDEXED_INDEX_COUNT_2_TO_EXP 32
-#endif
-#ifndef D3D11_REQ_DRAW_VERTEX_COUNT_2_TO_EXP
-# define D3D11_REQ_DRAW_VERTEX_COUNT_2_TO_EXP 32
-#endif
-#ifndef D3D10_1_STANDARD_VERTEX_ELEMENT_COUNT
-# define D3D10_1_STANDARD_VERTEX_ELEMENT_COUNT 32
-#endif
-#ifndef D3D11_STANDARD_VERTEX_ELEMENT_COUNT
-# define D3D11_STANDARD_VERTEX_ELEMENT_COUNT 32
-#endif
-#ifndef D3D10_1_SO_BUFFER_SLOT_COUNT
-# define D3D10_1_SO_BUFFER_SLOT_COUNT 4
-#endif
-#ifndef D3D11_SO_BUFFER_SLOT_COUNT
-# define D3D11_SO_BUFFER_SLOT_COUNT 4
-#endif
-#ifndef D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT
-# define D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT 14
-#endif
-#ifndef D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT
-# define D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT 16
-#endif
-#ifndef D3D11_COMMONSHADER_TEXEL_OFFSET_MAX_NEGATIVE
-# define D3D11_COMMONSHADER_TEXEL_OFFSET_MAX_NEGATIVE -8
-#endif
-#ifndef D3D11_COMMONSHADER_TEXEL_OFFSET_MAX_POSITIVE
-# define D3D11_COMMONSHADER_TEXEL_OFFSET_MAX_POSITIVE 7
-#endif
-#ifndef D3D11_REQ_CONSTANT_BUFFER_ELEMENT_COUNT
-# define D3D11_REQ_CONSTANT_BUFFER_ELEMENT_COUNT 4096
-#endif
-#ifndef D3D11_PS_INPUT_REGISTER_COUNT
-# define D3D11_PS_INPUT_REGISTER_COUNT 32
-#endif
-#ifndef D3D10_1_VS_OUTPUT_REGISTER_COUNT
-# define D3D10_1_VS_OUTPUT_REGISTER_COUNT 32
-#endif
-#if defined(ANGLE_MINGW32_COMPAT)
-static const IID WKPDID_D3DDebugObjectName = { 0x429b8c22, 0x9188, 0x4b0c, 0x87, 0x42, 0xac, 0xb0, 0xbf, 0x85, 0xc2, 0x00 };
-#endif
+#include "libANGLE/renderer/driver_utils.h"
+#include "platform/Platform.h"
+#include "platform/WorkaroundsD3D.h"
namespace rx
{
-namespace gl_d3d11
-{
-
-D3D11_BLEND ConvertBlendFunc(GLenum glBlend, bool isAlpha)
-{
- D3D11_BLEND d3dBlend = D3D11_BLEND_ZERO;
-
- switch (glBlend)
- {
- case GL_ZERO: d3dBlend = D3D11_BLEND_ZERO; break;
- case GL_ONE: d3dBlend = D3D11_BLEND_ONE; break;
- case GL_SRC_COLOR: d3dBlend = (isAlpha ? D3D11_BLEND_SRC_ALPHA : D3D11_BLEND_SRC_COLOR); break;
- case GL_ONE_MINUS_SRC_COLOR: d3dBlend = (isAlpha ? D3D11_BLEND_INV_SRC_ALPHA : D3D11_BLEND_INV_SRC_COLOR); break;
- case GL_DST_COLOR: d3dBlend = (isAlpha ? D3D11_BLEND_DEST_ALPHA : D3D11_BLEND_DEST_COLOR); break;
- case GL_ONE_MINUS_DST_COLOR: d3dBlend = (isAlpha ? D3D11_BLEND_INV_DEST_ALPHA : D3D11_BLEND_INV_DEST_COLOR); break;
- case GL_SRC_ALPHA: d3dBlend = D3D11_BLEND_SRC_ALPHA; break;
- case GL_ONE_MINUS_SRC_ALPHA: d3dBlend = D3D11_BLEND_INV_SRC_ALPHA; break;
- case GL_DST_ALPHA: d3dBlend = D3D11_BLEND_DEST_ALPHA; break;
- case GL_ONE_MINUS_DST_ALPHA: d3dBlend = D3D11_BLEND_INV_DEST_ALPHA; break;
- case GL_CONSTANT_COLOR: d3dBlend = D3D11_BLEND_BLEND_FACTOR; break;
- case GL_ONE_MINUS_CONSTANT_COLOR: d3dBlend = D3D11_BLEND_INV_BLEND_FACTOR; break;
- case GL_CONSTANT_ALPHA: d3dBlend = D3D11_BLEND_BLEND_FACTOR; break;
- case GL_ONE_MINUS_CONSTANT_ALPHA: d3dBlend = D3D11_BLEND_INV_BLEND_FACTOR; break;
- case GL_SRC_ALPHA_SATURATE: d3dBlend = D3D11_BLEND_SRC_ALPHA_SAT; break;
- default: UNREACHABLE();
- }
-
- return d3dBlend;
-}
-
-D3D11_BLEND_OP ConvertBlendOp(GLenum glBlendOp)
-{
- D3D11_BLEND_OP d3dBlendOp = D3D11_BLEND_OP_ADD;
-
- switch (glBlendOp)
- {
- case GL_FUNC_ADD: d3dBlendOp = D3D11_BLEND_OP_ADD; break;
- case GL_FUNC_SUBTRACT: d3dBlendOp = D3D11_BLEND_OP_SUBTRACT; break;
- case GL_FUNC_REVERSE_SUBTRACT: d3dBlendOp = D3D11_BLEND_OP_REV_SUBTRACT; break;
- case GL_MIN: d3dBlendOp = D3D11_BLEND_OP_MIN; break;
- case GL_MAX: d3dBlendOp = D3D11_BLEND_OP_MAX; break;
- default: UNREACHABLE();
- }
-
- return d3dBlendOp;
-}
-
-UINT8 ConvertColorMask(bool red, bool green, bool blue, bool alpha)
-{
- UINT8 mask = 0;
- if (red)
- {
- mask |= D3D11_COLOR_WRITE_ENABLE_RED;
- }
- if (green)
- {
- mask |= D3D11_COLOR_WRITE_ENABLE_GREEN;
- }
- if (blue)
- {
- mask |= D3D11_COLOR_WRITE_ENABLE_BLUE;
- }
- if (alpha)
- {
- mask |= D3D11_COLOR_WRITE_ENABLE_ALPHA;
- }
- return mask;
-}
-
-D3D11_CULL_MODE ConvertCullMode(bool cullEnabled, GLenum cullMode)
-{
- D3D11_CULL_MODE cull = D3D11_CULL_NONE;
-
- if (cullEnabled)
- {
- switch (cullMode)
- {
- case GL_FRONT: cull = D3D11_CULL_FRONT; break;
- case GL_BACK: cull = D3D11_CULL_BACK; break;
- case GL_FRONT_AND_BACK: cull = D3D11_CULL_NONE; break;
- default: UNREACHABLE();
- }
- }
- else
- {
- cull = D3D11_CULL_NONE;
- }
-
- return cull;
-}
-
-D3D11_COMPARISON_FUNC ConvertComparison(GLenum comparison)
-{
- D3D11_COMPARISON_FUNC d3dComp = D3D11_COMPARISON_NEVER;
- switch (comparison)
- {
- case GL_NEVER: d3dComp = D3D11_COMPARISON_NEVER; break;
- case GL_ALWAYS: d3dComp = D3D11_COMPARISON_ALWAYS; break;
- case GL_LESS: d3dComp = D3D11_COMPARISON_LESS; break;
- case GL_LEQUAL: d3dComp = D3D11_COMPARISON_LESS_EQUAL; break;
- case GL_EQUAL: d3dComp = D3D11_COMPARISON_EQUAL; break;
- case GL_GREATER: d3dComp = D3D11_COMPARISON_GREATER; break;
- case GL_GEQUAL: d3dComp = D3D11_COMPARISON_GREATER_EQUAL; break;
- case GL_NOTEQUAL: d3dComp = D3D11_COMPARISON_NOT_EQUAL; break;
- default: UNREACHABLE();
- }
-
- return d3dComp;
-}
-
-D3D11_DEPTH_WRITE_MASK ConvertDepthMask(bool depthWriteEnabled)
-{
- return depthWriteEnabled ? D3D11_DEPTH_WRITE_MASK_ALL : D3D11_DEPTH_WRITE_MASK_ZERO;
-}
-
-UINT8 ConvertStencilMask(GLuint stencilmask)
-{
- return static_cast<UINT8>(stencilmask);
-}
-
-D3D11_STENCIL_OP ConvertStencilOp(GLenum stencilOp)
-{
- D3D11_STENCIL_OP d3dStencilOp = D3D11_STENCIL_OP_KEEP;
-
- switch (stencilOp)
- {
- case GL_ZERO: d3dStencilOp = D3D11_STENCIL_OP_ZERO; break;
- case GL_KEEP: d3dStencilOp = D3D11_STENCIL_OP_KEEP; break;
- case GL_REPLACE: d3dStencilOp = D3D11_STENCIL_OP_REPLACE; break;
- case GL_INCR: d3dStencilOp = D3D11_STENCIL_OP_INCR_SAT; break;
- case GL_DECR: d3dStencilOp = D3D11_STENCIL_OP_DECR_SAT; break;
- case GL_INVERT: d3dStencilOp = D3D11_STENCIL_OP_INVERT; break;
- case GL_INCR_WRAP: d3dStencilOp = D3D11_STENCIL_OP_INCR; break;
- case GL_DECR_WRAP: d3dStencilOp = D3D11_STENCIL_OP_DECR; break;
- default: UNREACHABLE();
- }
-
- return d3dStencilOp;
-}
-
-D3D11_FILTER ConvertFilter(GLenum minFilter, GLenum magFilter, float maxAnisotropy, GLenum comparisonMode)
-{
- bool comparison = comparisonMode != GL_NONE;
-
- if (maxAnisotropy > 1.0f)
- {
- return D3D11_ENCODE_ANISOTROPIC_FILTER(static_cast<D3D11_COMPARISON_FUNC>(comparison));
- }
- else
- {
- D3D11_FILTER_TYPE dxMin = D3D11_FILTER_TYPE_POINT;
- D3D11_FILTER_TYPE dxMip = D3D11_FILTER_TYPE_POINT;
- switch (minFilter)
- {
- case GL_NEAREST: dxMin = D3D11_FILTER_TYPE_POINT; dxMip = D3D11_FILTER_TYPE_POINT; break;
- case GL_LINEAR: dxMin = D3D11_FILTER_TYPE_LINEAR; dxMip = D3D11_FILTER_TYPE_POINT; break;
- case GL_NEAREST_MIPMAP_NEAREST: dxMin = D3D11_FILTER_TYPE_POINT; dxMip = D3D11_FILTER_TYPE_POINT; break;
- case GL_LINEAR_MIPMAP_NEAREST: dxMin = D3D11_FILTER_TYPE_LINEAR; dxMip = D3D11_FILTER_TYPE_POINT; break;
- case GL_NEAREST_MIPMAP_LINEAR: dxMin = D3D11_FILTER_TYPE_POINT; dxMip = D3D11_FILTER_TYPE_LINEAR; break;
- case GL_LINEAR_MIPMAP_LINEAR: dxMin = D3D11_FILTER_TYPE_LINEAR; dxMip = D3D11_FILTER_TYPE_LINEAR; break;
- default: UNREACHABLE();
- }
-
- D3D11_FILTER_TYPE dxMag = D3D11_FILTER_TYPE_POINT;
- switch (magFilter)
- {
- case GL_NEAREST: dxMag = D3D11_FILTER_TYPE_POINT; break;
- case GL_LINEAR: dxMag = D3D11_FILTER_TYPE_LINEAR; break;
- default: UNREACHABLE();
- }
-
- return D3D11_ENCODE_BASIC_FILTER(dxMin, dxMag, dxMip, static_cast<D3D11_COMPARISON_FUNC>(comparison));
- }
-}
-
-D3D11_TEXTURE_ADDRESS_MODE ConvertTextureWrap(GLenum wrap)
-{
- switch (wrap)
- {
- case GL_REPEAT: return D3D11_TEXTURE_ADDRESS_WRAP;
- case GL_CLAMP_TO_EDGE: return D3D11_TEXTURE_ADDRESS_CLAMP;
- case GL_MIRRORED_REPEAT: return D3D11_TEXTURE_ADDRESS_MIRROR;
- default: UNREACHABLE();
- }
-
- return D3D11_TEXTURE_ADDRESS_WRAP;
-}
-
-D3D11_QUERY ConvertQueryType(GLenum queryType)
-{
- switch (queryType)
- {
- case GL_ANY_SAMPLES_PASSED_EXT:
- case GL_ANY_SAMPLES_PASSED_CONSERVATIVE_EXT: return D3D11_QUERY_OCCLUSION;
- case GL_TRANSFORM_FEEDBACK_PRIMITIVES_WRITTEN: return D3D11_QUERY_SO_STATISTICS;
- case GL_TIME_ELAPSED_EXT:
- // Two internal queries are also created for begin/end timestamps
- return D3D11_QUERY_TIMESTAMP_DISJOINT;
- default: UNREACHABLE(); return D3D11_QUERY_EVENT;
- }
-}
-
-} // namespace gl_d3d11
-
namespace d3d11_gl
{
-
namespace
{
+// Standard D3D sample positions from
+// https://msdn.microsoft.com/en-us/library/windows/desktop/ff476218.aspx
+using SamplePositionsArray = std::array<float, 32>;
+static constexpr std::array<SamplePositionsArray, 5> kSamplePositions = {
+ {{{0.5f, 0.5f}},
+ {{0.75f, 0.75f, 0.25f, 0.25f}},
+ {{0.375f, 0.125f, 0.875f, 0.375f, 0.125f, 0.625f, 0.625f, 0.875f}},
+ {{0.5625f, 0.3125f, 0.4375f, 0.6875f, 0.8125f, 0.5625f, 0.3125f, 0.1875f, 0.1875f, 0.8125f,
+ 0.0625f, 0.4375f, 0.6875f, 0.9375f, 0.9375f, 0.0625f}},
+ {{0.5625f, 0.5625f, 0.4375f, 0.3125f, 0.3125f, 0.625f, 0.75f, 0.4375f,
+ 0.1875f, 0.375f, 0.625f, 0.8125f, 0.8125f, 0.6875f, 0.6875f, 0.1875f,
+ 0.375f, 0.875f, 0.5f, 0.0625f, 0.25f, 0.125f, 0.125f, 0.75f,
+ 0.0f, 0.5f, 0.9375f, 0.25f, 0.875f, 0.9375f, 0.0625f, 0.0f}}}};
// Helper functor for querying DXGI support. Saves passing the parameters repeatedly.
class DXGISupportHelper : angle::NonCopyable
{
public:
DXGISupportHelper(ID3D11Device *device, D3D_FEATURE_LEVEL featureLevel)
- : mDevice(device),
- mFeatureLevel(featureLevel)
+ : mDevice(device), mFeatureLevel(featureLevel)
{
}
@@ -347,7 +80,7 @@ class DXGISupportHelper : angle::NonCopyable
else
{
// TODO(jmadill): find out why we fail this call sometimes in FL9_3
- // ERR("Error checking format support for format 0x%x", dxgiFormat);
+ // ERR() << "Error checking format support for format 0x" << std::hex << dxgiFormat;
}
}
@@ -359,93 +92,46 @@ class DXGISupportHelper : angle::NonCopyable
D3D_FEATURE_LEVEL mFeatureLevel;
};
-} // anonymous namespace
-
-unsigned int GetReservedVertexUniformVectors(D3D_FEATURE_LEVEL featureLevel)
-{
- switch (featureLevel)
- {
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0:
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0:
- return 0;
-
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1:
- return 3; // dx_ViewAdjust, dx_ViewCoords and dx_ViewScale
-
- default:
- UNREACHABLE();
- return 0;
- }
-}
-
-unsigned int GetReservedFragmentUniformVectors(D3D_FEATURE_LEVEL featureLevel)
-{
- switch (featureLevel)
- {
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0:
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0:
- return 0;
-
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1:
- return 3;
-
- default:
- UNREACHABLE();
- return 0;
- }
-}
-
-GLint GetMaximumClientVersion(D3D_FEATURE_LEVEL featureLevel)
-{
- switch (featureLevel)
- {
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0:
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return 3;
-
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1: return 2;
-
- default: UNREACHABLE(); return 0;
- }
-}
-
-static gl::TextureCaps GenerateTextureFormatCaps(GLint maxClientVersion, GLenum internalFormat, ID3D11Device *device, const Renderer11DeviceCaps &renderer11DeviceCaps)
+gl::TextureCaps GenerateTextureFormatCaps(gl::Version maxClientVersion,
+ GLenum internalFormat,
+ ID3D11Device *device,
+ const Renderer11DeviceCaps &renderer11DeviceCaps)
{
gl::TextureCaps textureCaps;
DXGISupportHelper support(device, renderer11DeviceCaps.featureLevel);
- const d3d11::TextureFormat &formatInfo =
- d3d11::GetTextureFormatInfo(internalFormat, renderer11DeviceCaps);
+ const d3d11::Format &formatInfo = d3d11::Format::Get(internalFormat, renderer11DeviceCaps);
- const gl::InternalFormat &internalFormatInfo = gl::GetInternalFormatInfo(internalFormat);
+ const gl::InternalFormat &internalFormatInfo = gl::GetSizedInternalFormatInfo(internalFormat);
UINT texSupportMask = D3D11_FORMAT_SUPPORT_TEXTURE2D;
if (internalFormatInfo.depthBits == 0 && internalFormatInfo.stencilBits == 0)
{
texSupportMask |= D3D11_FORMAT_SUPPORT_TEXTURECUBE;
- if (maxClientVersion > 2)
+ if (maxClientVersion.major > 2)
{
texSupportMask |= D3D11_FORMAT_SUPPORT_TEXTURE3D;
}
}
textureCaps.texturable = support.query(formatInfo.texFormat, texSupportMask);
- textureCaps.filterable = support.query(formatInfo.srvFormat, D3D11_FORMAT_SUPPORT_SHADER_SAMPLE);
- textureCaps.renderable = (support.query(formatInfo.rtvFormat, D3D11_FORMAT_SUPPORT_RENDER_TARGET)) ||
- (support.query(formatInfo.dsvFormat, D3D11_FORMAT_SUPPORT_DEPTH_STENCIL));
+ textureCaps.filterable =
+ support.query(formatInfo.srvFormat, D3D11_FORMAT_SUPPORT_SHADER_SAMPLE);
+ textureCaps.renderable =
+ (support.query(formatInfo.rtvFormat, D3D11_FORMAT_SUPPORT_RENDER_TARGET)) ||
+ (support.query(formatInfo.dsvFormat, D3D11_FORMAT_SUPPORT_DEPTH_STENCIL));
- if (support.query(formatInfo.renderFormat, D3D11_FORMAT_SUPPORT_MULTISAMPLE_RENDERTARGET))
+ DXGI_FORMAT renderFormat = DXGI_FORMAT_UNKNOWN;
+ if (formatInfo.dsvFormat != DXGI_FORMAT_UNKNOWN)
+ {
+ renderFormat = formatInfo.dsvFormat;
+ }
+ else if (formatInfo.rtvFormat != DXGI_FORMAT_UNKNOWN)
+ {
+ renderFormat = formatInfo.rtvFormat;
+ }
+ if (renderFormat != DXGI_FORMAT_UNKNOWN &&
+ support.query(renderFormat, D3D11_FORMAT_SUPPORT_MULTISAMPLE_RENDERTARGET))
{
// Assume 1x
textureCaps.sampleCounts.insert(1);
@@ -454,7 +140,8 @@ static gl::TextureCaps GenerateTextureFormatCaps(GLint maxClientVersion, GLenum
sampleCount *= 2)
{
UINT qualityCount = 0;
- if (SUCCEEDED(device->CheckMultisampleQualityLevels(formatInfo.renderFormat, sampleCount, &qualityCount)))
+ if (SUCCEEDED(device->CheckMultisampleQualityLevels(renderFormat, sampleCount,
+ &qualityCount)))
{
// Assume we always support lower sample counts
if (qualityCount == 0)
@@ -469,691 +156,1124 @@ static gl::TextureCaps GenerateTextureFormatCaps(GLint maxClientVersion, GLenum
return textureCaps;
}
-static bool GetNPOTTextureSupport(D3D_FEATURE_LEVEL featureLevel)
+bool GetNPOTTextureSupport(D3D_FEATURE_LEVEL featureLevel)
{
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0:
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return true;
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return true;
// From http://msdn.microsoft.com/en-us/library/windows/desktop/ff476876.aspx
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1: return false;
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return false;
- default: UNREACHABLE(); return false;
+ default:
+ UNREACHABLE();
+ return false;
}
}
-static float GetMaximumAnisotropy(D3D_FEATURE_LEVEL featureLevel)
+float GetMaximumAnisotropy(D3D_FEATURE_LEVEL featureLevel)
{
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0: return D3D11_MAX_MAXANISOTROPY;
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return D3D11_MAX_MAXANISOTROPY;
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return D3D10_MAX_MAXANISOTROPY;
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return D3D10_MAX_MAXANISOTROPY;
// From http://msdn.microsoft.com/en-us/library/windows/desktop/ff476876.aspx
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2: return 16;
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ return 16;
- case D3D_FEATURE_LEVEL_9_1: return D3D_FL9_1_DEFAULT_MAX_ANISOTROPY;
+ case D3D_FEATURE_LEVEL_9_1:
+ return D3D_FL9_1_DEFAULT_MAX_ANISOTROPY;
- default: UNREACHABLE(); return 0;
+ default:
+ UNREACHABLE();
+ return 0;
}
}
-static bool GetOcclusionQuerySupport(D3D_FEATURE_LEVEL featureLevel)
+bool GetOcclusionQuerySupport(D3D_FEATURE_LEVEL featureLevel)
{
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0:
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return true;
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return true;
- // From http://msdn.microsoft.com/en-us/library/windows/desktop/ff476150.aspx ID3D11Device::CreateQuery
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2: return true;
- case D3D_FEATURE_LEVEL_9_1: return false;
+ // From http://msdn.microsoft.com/en-us/library/windows/desktop/ff476150.aspx
+ // ID3D11Device::CreateQuery
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ return true;
+ case D3D_FEATURE_LEVEL_9_1:
+ return false;
- default: UNREACHABLE(); return false;
+ default:
+ UNREACHABLE();
+ return false;
}
}
-static bool GetEventQuerySupport(D3D_FEATURE_LEVEL featureLevel)
+bool GetEventQuerySupport(D3D_FEATURE_LEVEL featureLevel)
{
- // From http://msdn.microsoft.com/en-us/library/windows/desktop/ff476150.aspx ID3D11Device::CreateQuery
+ // From http://msdn.microsoft.com/en-us/library/windows/desktop/ff476150.aspx
+ // ID3D11Device::CreateQuery
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0:
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0:
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1: return true;
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return true;
- default: UNREACHABLE(); return false;
+ default:
+ UNREACHABLE();
+ return false;
}
}
-static bool GetInstancingSupport(D3D_FEATURE_LEVEL featureLevel)
+bool GetInstancingSupport(D3D_FEATURE_LEVEL featureLevel)
{
- // From http://msdn.microsoft.com/en-us/library/windows/desktop/ff476150.aspx ID3D11Device::CreateInputLayout
+ // From http://msdn.microsoft.com/en-us/library/windows/desktop/ff476150.aspx
+ // ID3D11Device::CreateInputLayout
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0:
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return true;
-
- // Feature Level 9_3 supports instancing, but slot 0 in the input layout must not be instanced.
- // D3D9 has a similar restriction, where stream 0 must not be instanced.
- // This restriction can be worked around by remapping any non-instanced slot to slot 0.
- // This works because HLSL uses shader semantics to match the vertex inputs to the elements in the input layout, rather than the slots.
- // Note that we only support instancing via ANGLE_instanced_array on 9_3, since 9_3 doesn't support OpenGL ES 3.0
- case D3D_FEATURE_LEVEL_9_3: return true;
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return true;
+
+ // Feature Level 9_3 supports instancing, but slot 0 in the input layout must not be
+ // instanced.
+ // D3D9 has a similar restriction, where stream 0 must not be instanced.
+ // This restriction can be worked around by remapping any non-instanced slot to slot
+ // 0.
+ // This works because HLSL uses shader semantics to match the vertex inputs to the
+ // elements in the input layout, rather than the slots.
+ // Note that we only support instancing via ANGLE_instanced_array on 9_3, since 9_3
+ // doesn't support OpenGL ES 3.0
+ case D3D_FEATURE_LEVEL_9_3:
+ return true;
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1: return false;
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return false;
- default: UNREACHABLE(); return false;
+ default:
+ UNREACHABLE();
+ return false;
}
}
-static bool GetFramebufferMultisampleSupport(D3D_FEATURE_LEVEL featureLevel)
+bool GetFramebufferMultisampleSupport(D3D_FEATURE_LEVEL featureLevel)
{
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0:
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return true;
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return true;
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1: return false;
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return false;
- default: UNREACHABLE(); return false;
+ default:
+ UNREACHABLE();
+ return false;
}
}
-static bool GetFramebufferBlitSupport(D3D_FEATURE_LEVEL featureLevel)
+bool GetFramebufferBlitSupport(D3D_FEATURE_LEVEL featureLevel)
{
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0:
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return true;
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return true;
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1: return false;
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return false;
- default: UNREACHABLE(); return false;
+ default:
+ UNREACHABLE();
+ return false;
}
}
-static bool GetDerivativeInstructionSupport(D3D_FEATURE_LEVEL featureLevel)
+bool GetDerivativeInstructionSupport(D3D_FEATURE_LEVEL featureLevel)
{
- // http://msdn.microsoft.com/en-us/library/windows/desktop/bb509588.aspx states that shader model
+ // http://msdn.microsoft.com/en-us/library/windows/desktop/bb509588.aspx states that
+ // shader model
// ps_2_x is required for the ddx (and other derivative functions).
- // http://msdn.microsoft.com/en-us/library/windows/desktop/ff476876.aspx states that feature level
+ // http://msdn.microsoft.com/en-us/library/windows/desktop/ff476876.aspx states that
+ // feature level
// 9.3 supports shader model ps_2_x.
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0:
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0:
- case D3D_FEATURE_LEVEL_9_3: return true;
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1: return false;
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ case D3D_FEATURE_LEVEL_9_3:
+ return true;
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return false;
- default: UNREACHABLE(); return false;
+ default:
+ UNREACHABLE();
+ return false;
}
}
-static bool GetShaderTextureLODSupport(D3D_FEATURE_LEVEL featureLevel)
+bool GetShaderTextureLODSupport(D3D_FEATURE_LEVEL featureLevel)
{
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0:
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return true;
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return true;
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1: return false;
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return false;
- default: UNREACHABLE(); return false;
+ default:
+ UNREACHABLE();
+ return false;
}
}
-static size_t GetMaximumSimultaneousRenderTargets(D3D_FEATURE_LEVEL featureLevel)
+size_t GetMaximumSimultaneousRenderTargets(D3D_FEATURE_LEVEL featureLevel)
{
- // From http://msdn.microsoft.com/en-us/library/windows/desktop/ff476150.aspx ID3D11Device::CreateInputLayout
+ // From http://msdn.microsoft.com/en-us/library/windows/desktop/ff476150.aspx
+ // ID3D11Device::CreateInputLayout
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0: return D3D11_SIMULTANEOUS_RENDER_TARGET_COUNT;
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return D3D11_SIMULTANEOUS_RENDER_TARGET_COUNT;
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return D3D10_SIMULTANEOUS_RENDER_TARGET_COUNT;
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return D3D10_SIMULTANEOUS_RENDER_TARGET_COUNT;
- case D3D_FEATURE_LEVEL_9_3: return D3D_FL9_3_SIMULTANEOUS_RENDER_TARGET_COUNT;
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1: return D3D_FL9_1_SIMULTANEOUS_RENDER_TARGET_COUNT;
+ case D3D_FEATURE_LEVEL_9_3:
+ return D3D_FL9_3_SIMULTANEOUS_RENDER_TARGET_COUNT;
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return D3D_FL9_1_SIMULTANEOUS_RENDER_TARGET_COUNT;
- default: UNREACHABLE(); return 0;
+ default:
+ UNREACHABLE();
+ return 0;
}
}
-static size_t GetMaximum2DTextureSize(D3D_FEATURE_LEVEL featureLevel)
+size_t GetMaximum2DTextureSize(D3D_FEATURE_LEVEL featureLevel)
{
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0: return D3D11_REQ_TEXTURE2D_U_OR_V_DIMENSION;
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return D3D11_REQ_TEXTURE2D_U_OR_V_DIMENSION;
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return D3D10_REQ_TEXTURE2D_U_OR_V_DIMENSION;
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return D3D10_REQ_TEXTURE2D_U_OR_V_DIMENSION;
- case D3D_FEATURE_LEVEL_9_3: return D3D_FL9_3_REQ_TEXTURE2D_U_OR_V_DIMENSION;
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1: return D3D_FL9_1_REQ_TEXTURE2D_U_OR_V_DIMENSION;
+ case D3D_FEATURE_LEVEL_9_3:
+ return D3D_FL9_3_REQ_TEXTURE2D_U_OR_V_DIMENSION;
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return D3D_FL9_1_REQ_TEXTURE2D_U_OR_V_DIMENSION;
- default: UNREACHABLE(); return 0;
+ default:
+ UNREACHABLE();
+ return 0;
}
}
-static size_t GetMaximumCubeMapTextureSize(D3D_FEATURE_LEVEL featureLevel)
+size_t GetMaximumCubeMapTextureSize(D3D_FEATURE_LEVEL featureLevel)
{
switch (featureLevel)
{
-#if defined(ANGLE_ENABLE_D3D11_1)
- case D3D_FEATURE_LEVEL_11_1:
-#endif
- case D3D_FEATURE_LEVEL_11_0: return D3D11_REQ_TEXTURECUBE_DIMENSION;
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return D3D11_REQ_TEXTURECUBE_DIMENSION;
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return D3D10_REQ_TEXTURECUBE_DIMENSION;
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return D3D10_REQ_TEXTURECUBE_DIMENSION;
- case D3D_FEATURE_LEVEL_9_3: return D3D_FL9_3_REQ_TEXTURECUBE_DIMENSION;
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1: return D3D_FL9_1_REQ_TEXTURECUBE_DIMENSION;
+ case D3D_FEATURE_LEVEL_9_3:
+ return D3D_FL9_3_REQ_TEXTURECUBE_DIMENSION;
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return D3D_FL9_1_REQ_TEXTURECUBE_DIMENSION;
- default: UNREACHABLE(); return 0;
+ default:
+ UNREACHABLE();
+ return 0;
}
}
-static size_t GetMaximum2DTextureArraySize(D3D_FEATURE_LEVEL featureLevel)
+size_t GetMaximum2DTextureArraySize(D3D_FEATURE_LEVEL featureLevel)
{
switch (featureLevel)
{
-#if defined(ANGLE_ENABLE_D3D11_1)
- case D3D_FEATURE_LEVEL_11_1:
-#endif
- case D3D_FEATURE_LEVEL_11_0: return D3D11_REQ_TEXTURE2D_ARRAY_AXIS_DIMENSION;
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return D3D11_REQ_TEXTURE2D_ARRAY_AXIS_DIMENSION;
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return D3D10_REQ_TEXTURE2D_ARRAY_AXIS_DIMENSION;
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return D3D10_REQ_TEXTURE2D_ARRAY_AXIS_DIMENSION;
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1: return 0;
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return 0;
- default: UNREACHABLE(); return 0;
+ default:
+ UNREACHABLE();
+ return 0;
}
}
-static size_t GetMaximum3DTextureSize(D3D_FEATURE_LEVEL featureLevel)
+size_t GetMaximum3DTextureSize(D3D_FEATURE_LEVEL featureLevel)
{
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0: return D3D11_REQ_TEXTURE3D_U_V_OR_W_DIMENSION;
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return D3D11_REQ_TEXTURE3D_U_V_OR_W_DIMENSION;
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return D3D10_REQ_TEXTURE3D_U_V_OR_W_DIMENSION;
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return D3D10_REQ_TEXTURE3D_U_V_OR_W_DIMENSION;
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1: return D3D_FL9_1_REQ_TEXTURE3D_U_V_OR_W_DIMENSION;
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return D3D_FL9_1_REQ_TEXTURE3D_U_V_OR_W_DIMENSION;
- default: UNREACHABLE(); return 0;
+ default:
+ UNREACHABLE();
+ return 0;
}
}
-static size_t GetMaximumViewportSize(D3D_FEATURE_LEVEL featureLevel)
+size_t GetMaximumViewportSize(D3D_FEATURE_LEVEL featureLevel)
{
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0: return D3D11_VIEWPORT_BOUNDS_MAX;
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return D3D11_VIEWPORT_BOUNDS_MAX;
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return D3D10_VIEWPORT_BOUNDS_MAX;
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return D3D10_VIEWPORT_BOUNDS_MAX;
- // No constants for D3D11 Feature Level 9 viewport size limits, use the maximum texture sizes
- case D3D_FEATURE_LEVEL_9_3: return D3D_FL9_3_REQ_TEXTURE2D_U_OR_V_DIMENSION;
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1: return D3D_FL9_1_REQ_TEXTURE2D_U_OR_V_DIMENSION;
+ // No constants for D3D11 Feature Level 9 viewport size limits, use the maximum
+ // texture sizes
+ case D3D_FEATURE_LEVEL_9_3:
+ return D3D_FL9_3_REQ_TEXTURE2D_U_OR_V_DIMENSION;
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return D3D_FL9_1_REQ_TEXTURE2D_U_OR_V_DIMENSION;
- default: UNREACHABLE(); return 0;
+ default:
+ UNREACHABLE();
+ return 0;
}
}
-static size_t GetMaximumDrawIndexedIndexCount(D3D_FEATURE_LEVEL featureLevel)
+size_t GetMaximumDrawIndexedIndexCount(D3D_FEATURE_LEVEL featureLevel)
{
- // D3D11 allows up to 2^32 elements, but we report max signed int for convenience since that's what's
+ // D3D11 allows up to 2^32 elements, but we report max signed int for convenience since
+ // that's what's
// returned from glGetInteger
- static_assert(D3D11_REQ_DRAWINDEXED_INDEX_COUNT_2_TO_EXP == 32, "Unexpected D3D11 constant value.");
- static_assert(D3D10_REQ_DRAWINDEXED_INDEX_COUNT_2_TO_EXP == 32, "Unexpected D3D11 constant value.");
+ static_assert(D3D11_REQ_DRAWINDEXED_INDEX_COUNT_2_TO_EXP == 32,
+ "Unexpected D3D11 constant value.");
+ static_assert(D3D10_REQ_DRAWINDEXED_INDEX_COUNT_2_TO_EXP == 32,
+ "Unexpected D3D11 constant value.");
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0:
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return std::numeric_limits<GLint>::max();
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return std::numeric_limits<GLint>::max();
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2: return D3D_FL9_2_IA_PRIMITIVE_MAX_COUNT;
- case D3D_FEATURE_LEVEL_9_1: return D3D_FL9_1_IA_PRIMITIVE_MAX_COUNT;
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ return D3D_FL9_2_IA_PRIMITIVE_MAX_COUNT;
+ case D3D_FEATURE_LEVEL_9_1:
+ return D3D_FL9_1_IA_PRIMITIVE_MAX_COUNT;
- default: UNREACHABLE(); return 0;
+ default:
+ UNREACHABLE();
+ return 0;
}
}
-static size_t GetMaximumDrawVertexCount(D3D_FEATURE_LEVEL featureLevel)
+size_t GetMaximumDrawVertexCount(D3D_FEATURE_LEVEL featureLevel)
{
- // D3D11 allows up to 2^32 elements, but we report max signed int for convenience since that's what's
+ // D3D11 allows up to 2^32 elements, but we report max signed int for convenience since
+ // that's what's
// returned from glGetInteger
static_assert(D3D11_REQ_DRAW_VERTEX_COUNT_2_TO_EXP == 32, "Unexpected D3D11 constant value.");
static_assert(D3D10_REQ_DRAW_VERTEX_COUNT_2_TO_EXP == 32, "Unexpected D3D11 constant value.");
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0:
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return std::numeric_limits<GLint>::max();
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return std::numeric_limits<GLint>::max();
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2: return D3D_FL9_2_IA_PRIMITIVE_MAX_COUNT;
- case D3D_FEATURE_LEVEL_9_1: return D3D_FL9_1_IA_PRIMITIVE_MAX_COUNT;
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ return D3D_FL9_2_IA_PRIMITIVE_MAX_COUNT;
+ case D3D_FEATURE_LEVEL_9_1:
+ return D3D_FL9_1_IA_PRIMITIVE_MAX_COUNT;
- default: UNREACHABLE(); return 0;
+ default:
+ UNREACHABLE();
+ return 0;
}
}
-static size_t GetMaximumVertexInputSlots(D3D_FEATURE_LEVEL featureLevel)
+size_t GetMaximumVertexInputSlots(D3D_FEATURE_LEVEL featureLevel)
{
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0: return D3D11_STANDARD_VERTEX_ELEMENT_COUNT;
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return D3D11_STANDARD_VERTEX_ELEMENT_COUNT;
- case D3D_FEATURE_LEVEL_10_1: return D3D10_1_STANDARD_VERTEX_ELEMENT_COUNT;
- case D3D_FEATURE_LEVEL_10_0: return D3D10_STANDARD_VERTEX_ELEMENT_COUNT;
+ case D3D_FEATURE_LEVEL_10_1:
+ return D3D10_1_STANDARD_VERTEX_ELEMENT_COUNT;
+ case D3D_FEATURE_LEVEL_10_0:
+ return D3D10_STANDARD_VERTEX_ELEMENT_COUNT;
- // From http://http://msdn.microsoft.com/en-us/library/windows/desktop/ff476876.aspx "Max Input Slots"
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1: return 16;
+ // From http://http://msdn.microsoft.com/en-us/library/windows/desktop/ff476876.aspx
+ // "Max Input Slots"
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return 16;
- default: UNREACHABLE(); return 0;
+ default:
+ UNREACHABLE();
+ return 0;
}
}
-static size_t GetMaximumVertexUniformVectors(D3D_FEATURE_LEVEL featureLevel)
+size_t GetMaximumVertexUniformVectors(D3D_FEATURE_LEVEL featureLevel)
{
- // TODO(geofflang): Remove hard-coded limit once the gl-uniform-arrays test can pass
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0: return 1024; // D3D11_REQ_CONSTANT_BUFFER_ELEMENT_COUNT;
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return D3D11_REQ_CONSTANT_BUFFER_ELEMENT_COUNT;
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return 1024; // D3D10_REQ_CONSTANT_BUFFER_ELEMENT_COUNT;
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return D3D10_REQ_CONSTANT_BUFFER_ELEMENT_COUNT;
- // From http://msdn.microsoft.com/en-us/library/windows/desktop/ff476149.aspx ID3D11DeviceContext::VSSetConstantBuffers
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1:
- return 255 - d3d11_gl::GetReservedVertexUniformVectors(featureLevel);
+ // From http://msdn.microsoft.com/en-us/library/windows/desktop/ff476149.aspx
+ // ID3D11DeviceContext::VSSetConstantBuffers
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return 255 - d3d11_gl::GetReservedVertexUniformVectors(featureLevel);
- default: UNREACHABLE(); return 0;
+ default:
+ UNREACHABLE();
+ return 0;
}
}
-static size_t GetReservedVertexUniformBuffers()
-{
- // Reserve one buffer for the application uniforms, and one for driver uniforms
- return 2;
-}
-
-static size_t GetMaximumVertexUniformBlocks(D3D_FEATURE_LEVEL featureLevel)
+size_t GetMaximumVertexUniformBlocks(D3D_FEATURE_LEVEL featureLevel)
{
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0: return D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT - GetReservedVertexUniformBuffers();
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT -
+ d3d11::RESERVED_CONSTANT_BUFFER_SLOT_COUNT;
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return D3D10_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT - GetReservedVertexUniformBuffers();
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return D3D10_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT -
+ d3d11::RESERVED_CONSTANT_BUFFER_SLOT_COUNT;
- // Uniform blocks not supported on D3D11 Feature Level 9
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1: return 0;
+ // Uniform blocks not supported on D3D11 Feature Level 9
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return 0;
- default: UNREACHABLE(); return 0;
+ default:
+ UNREACHABLE();
+ return 0;
}
}
-static size_t GetReservedVertexOutputVectors(D3D_FEATURE_LEVEL featureLevel)
+size_t GetReservedVertexOutputVectors(D3D_FEATURE_LEVEL featureLevel)
{
- // According to The OpenGL ES Shading Language specifications
+ // According to The OpenGL ES Shading Language specifications
// (Language Version 1.00 section 10.16, Language Version 3.10 section 12.21)
// built-in special variables (e.g. gl_FragCoord, or gl_PointCoord)
- // which are statically used in the shader should be included in the variable packing algorithm.
+ // which are statically used in the shader should be included in the variable packing
+ // algorithm.
// Therefore, we should not reserve output vectors for them.
switch (featureLevel)
{
- // We must reserve one output vector for dx_Position.
- // We also reserve one for gl_Position, which we unconditionally output on Feature Levels 10_0+,
- // even if it's unused in the shader (e.g. for transform feedback). TODO: This could be improved.
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0:
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return 2;
+ // We must reserve one output vector for dx_Position.
+ // We also reserve one for gl_Position, which we unconditionally output on Feature
+ // Levels 10_0+,
+ // even if it's unused in the shader (e.g. for transform feedback). TODO: This could
+ // be improved.
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return 2;
- // Just reserve dx_Position on Feature Level 9, since we don't ever need to output gl_Position.
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1: return 1;
+ // Just reserve dx_Position on Feature Level 9, since we don't ever need to output
+ // gl_Position.
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return 1;
- default: UNREACHABLE(); return 0;
+ default:
+ UNREACHABLE();
+ return 0;
}
-
- return 1;
}
-static size_t GetMaximumVertexOutputVectors(D3D_FEATURE_LEVEL featureLevel)
+size_t GetMaximumVertexOutputVectors(D3D_FEATURE_LEVEL featureLevel)
{
- static_assert(gl::IMPLEMENTATION_MAX_VARYING_VECTORS == D3D11_VS_OUTPUT_REGISTER_COUNT, "Unexpected D3D11 constant value.");
+ static_assert(gl::IMPLEMENTATION_MAX_VARYING_VECTORS == D3D11_VS_OUTPUT_REGISTER_COUNT,
+ "Unexpected D3D11 constant value.");
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0: return D3D11_VS_OUTPUT_REGISTER_COUNT - GetReservedVertexOutputVectors(featureLevel);
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return D3D11_VS_OUTPUT_REGISTER_COUNT - GetReservedVertexOutputVectors(featureLevel);
- case D3D_FEATURE_LEVEL_10_1: return D3D10_1_VS_OUTPUT_REGISTER_COUNT - GetReservedVertexOutputVectors(featureLevel);
- case D3D_FEATURE_LEVEL_10_0: return D3D10_VS_OUTPUT_REGISTER_COUNT - GetReservedVertexOutputVectors(featureLevel);
+ case D3D_FEATURE_LEVEL_10_1:
+ return D3D10_1_VS_OUTPUT_REGISTER_COUNT - GetReservedVertexOutputVectors(featureLevel);
+ case D3D_FEATURE_LEVEL_10_0:
+ return D3D10_VS_OUTPUT_REGISTER_COUNT - GetReservedVertexOutputVectors(featureLevel);
- // Use Shader Model 2.X limits
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1: return 8 - GetReservedVertexOutputVectors(featureLevel);
+ // Use Shader Model 2.X limits
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return 8 - GetReservedVertexOutputVectors(featureLevel);
- default: UNREACHABLE(); return 0;
+ default:
+ UNREACHABLE();
+ return 0;
}
}
-static size_t GetMaximumVertexTextureUnits(D3D_FEATURE_LEVEL featureLevel)
+size_t GetMaximumVertexTextureUnits(D3D_FEATURE_LEVEL featureLevel)
{
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0: return D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT;
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT;
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return D3D10_COMMONSHADER_SAMPLER_SLOT_COUNT;
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return D3D10_COMMONSHADER_SAMPLER_SLOT_COUNT;
- // Vertex textures not supported on D3D11 Feature Level 9 according to
- // http://msdn.microsoft.com/en-us/library/windows/desktop/ff476149.aspx
- // ID3D11DeviceContext::VSSetSamplers and ID3D11DeviceContext::VSSetShaderResources
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1: return 0;
+ // Vertex textures not supported on D3D11 Feature Level 9 according to
+ // http://msdn.microsoft.com/en-us/library/windows/desktop/ff476149.aspx
+ // ID3D11DeviceContext::VSSetSamplers and ID3D11DeviceContext::VSSetShaderResources
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return 0;
- default: UNREACHABLE(); return 0;
+ default:
+ UNREACHABLE();
+ return 0;
}
}
-static size_t GetMaximumPixelUniformVectors(D3D_FEATURE_LEVEL featureLevel)
+size_t GetMaximumPixelUniformVectors(D3D_FEATURE_LEVEL featureLevel)
{
// TODO(geofflang): Remove hard-coded limit once the gl-uniform-arrays test can pass
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0: return 1024; // D3D11_REQ_CONSTANT_BUFFER_ELEMENT_COUNT;
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return 1024; // D3D11_REQ_CONSTANT_BUFFER_ELEMENT_COUNT;
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return 1024; // D3D10_REQ_CONSTANT_BUFFER_ELEMENT_COUNT;
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return 1024; // D3D10_REQ_CONSTANT_BUFFER_ELEMENT_COUNT;
- // From http://msdn.microsoft.com/en-us/library/windows/desktop/ff476149.aspx ID3D11DeviceContext::PSSetConstantBuffers
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1:
- return 32 - d3d11_gl::GetReservedFragmentUniformVectors(featureLevel);
+ // From http://msdn.microsoft.com/en-us/library/windows/desktop/ff476149.aspx
+ // ID3D11DeviceContext::PSSetConstantBuffers
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return 32 - d3d11_gl::GetReservedFragmentUniformVectors(featureLevel);
- default: UNREACHABLE(); return 0;
+ default:
+ UNREACHABLE();
+ return 0;
}
}
-static size_t GetReservedPixelUniformBuffers()
+size_t GetMaximumPixelUniformBlocks(D3D_FEATURE_LEVEL featureLevel)
{
- // Reserve one buffer for the application uniforms, and one for driver uniforms
- return 2;
+ switch (featureLevel)
+ {
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT -
+ d3d11::RESERVED_CONSTANT_BUFFER_SLOT_COUNT;
+
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return D3D10_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT -
+ d3d11::RESERVED_CONSTANT_BUFFER_SLOT_COUNT;
+
+ // Uniform blocks not supported on D3D11 Feature Level 9
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return 0;
+
+ default:
+ UNREACHABLE();
+ return 0;
+ }
+}
+
+size_t GetMaximumPixelInputVectors(D3D_FEATURE_LEVEL featureLevel)
+{
+ switch (featureLevel)
+ {
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return D3D11_PS_INPUT_REGISTER_COUNT - GetReservedVertexOutputVectors(featureLevel);
+
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return D3D10_PS_INPUT_REGISTER_COUNT - GetReservedVertexOutputVectors(featureLevel);
+
+ // Use Shader Model 2.X limits
+ case D3D_FEATURE_LEVEL_9_3:
+ return 8 - GetReservedVertexOutputVectors(featureLevel);
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return 8 - GetReservedVertexOutputVectors(featureLevel);
+
+ default:
+ UNREACHABLE();
+ return 0;
+ }
}
-static size_t GetMaximumPixelUniformBlocks(D3D_FEATURE_LEVEL featureLevel)
+size_t GetMaximumPixelTextureUnits(D3D_FEATURE_LEVEL featureLevel)
{
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0: return D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT - GetReservedPixelUniformBuffers();
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT;
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return D3D10_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT - GetReservedPixelUniformBuffers();
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return D3D10_COMMONSHADER_SAMPLER_SLOT_COUNT;
- // Uniform blocks not supported on D3D11 Feature Level 9
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1: return 0;
+ // http://msdn.microsoft.com/en-us/library/windows/desktop/ff476149.aspx
+ // ID3D11DeviceContext::PSSetShaderResources
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return 16;
- default: UNREACHABLE(); return 0;
+ default:
+ UNREACHABLE();
+ return 0;
}
}
-static size_t GetMaximumPixelInputVectors(D3D_FEATURE_LEVEL featureLevel)
+std::array<GLuint, 3> GetMaxComputeWorkGroupCount(D3D_FEATURE_LEVEL featureLevel)
{
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0: return D3D11_PS_INPUT_REGISTER_COUNT - GetReservedVertexOutputVectors(featureLevel);
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return {{D3D11_CS_DISPATCH_MAX_THREAD_GROUPS_PER_DIMENSION,
+ D3D11_CS_DISPATCH_MAX_THREAD_GROUPS_PER_DIMENSION,
+ D3D11_CS_DISPATCH_MAX_THREAD_GROUPS_PER_DIMENSION}};
+ break;
+ default:
+ return {{0, 0, 0}};
+ }
+}
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return D3D10_PS_INPUT_REGISTER_COUNT - GetReservedVertexOutputVectors(featureLevel);
+std::array<GLuint, 3> GetMaxComputeWorkGroupSize(D3D_FEATURE_LEVEL featureLevel)
+{
+ switch (featureLevel)
+ {
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return {{D3D11_CS_THREAD_GROUP_MAX_X, D3D11_CS_THREAD_GROUP_MAX_Y,
+ D3D11_CS_THREAD_GROUP_MAX_Z}};
+ break;
+ default:
+ return {{0, 0, 0}};
+ }
+}
- // Use Shader Model 2.X limits
- case D3D_FEATURE_LEVEL_9_3: return 8 - GetReservedVertexOutputVectors(featureLevel);
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1: return 8 - GetReservedVertexOutputVectors(featureLevel);
+size_t GetMaxComputeWorkGroupInvocations(D3D_FEATURE_LEVEL featureLevel)
+{
+ switch (featureLevel)
+ {
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return D3D11_CS_THREAD_GROUP_MAX_THREADS_PER_GROUP;
+ default:
+ return 0;
+ }
+}
- default: UNREACHABLE(); return 0;
+size_t GetMaximumComputeUniformVectors(D3D_FEATURE_LEVEL featureLevel)
+{
+ switch (featureLevel)
+ {
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return D3D11_REQ_CONSTANT_BUFFER_ELEMENT_COUNT;
+ default:
+ return 0;
}
}
-static size_t GetMaximumPixelTextureUnits(D3D_FEATURE_LEVEL featureLevel)
+size_t GetMaximumComputeUniformBlocks(D3D_FEATURE_LEVEL featureLevel)
{
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0: return D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT;
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT -
+ d3d11::RESERVED_CONSTANT_BUFFER_SLOT_COUNT;
+ default:
+ return 0;
+ }
+}
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return D3D10_COMMONSHADER_SAMPLER_SLOT_COUNT;
+size_t GetMaximumComputeTextureUnits(D3D_FEATURE_LEVEL featureLevel)
+{
+ switch (featureLevel)
+ {
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT;
+ default:
+ return 0;
+ }
+}
- // http://msdn.microsoft.com/en-us/library/windows/desktop/ff476149.aspx ID3D11DeviceContext::PSSetShaderResources
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1: return 16;
+size_t GetMaximumImageUnits(D3D_FEATURE_LEVEL featureLevel)
+{
+ switch (featureLevel)
+ {
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ // TODO(xinghua.cao@intel.com): Get a more accurate limit. For now using
+ // the minimum requirement for GLES 3.1.
+ return 4;
+ default:
+ return 0;
+ }
+}
- default: UNREACHABLE(); return 0;
+size_t GetMaximumComputeImageUniforms(D3D_FEATURE_LEVEL featureLevel)
+{
+ switch (featureLevel)
+ {
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ // TODO(xinghua.cao@intel.com): Get a more accurate limit. For now using
+ // the minimum requirement for GLES 3.1.
+ return 4;
+ default:
+ return 0;
}
}
-static int GetMinimumTexelOffset(D3D_FEATURE_LEVEL featureLevel)
+int GetMinimumTexelOffset(D3D_FEATURE_LEVEL featureLevel)
{
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0: return D3D11_COMMONSHADER_TEXEL_OFFSET_MAX_NEGATIVE;
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return D3D11_COMMONSHADER_TEXEL_OFFSET_MAX_NEGATIVE;
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return D3D10_COMMONSHADER_TEXEL_OFFSET_MAX_NEGATIVE;
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return D3D10_COMMONSHADER_TEXEL_OFFSET_MAX_NEGATIVE;
- // Sampling functions with offsets are not available below shader model 4.0.
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1: return 0;
+ // Sampling functions with offsets are not available below shader model 4.0.
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return 0;
- default: UNREACHABLE(); return 0;
+ default:
+ UNREACHABLE();
+ return 0;
}
}
-static int GetMaximumTexelOffset(D3D_FEATURE_LEVEL featureLevel)
+int GetMaximumTexelOffset(D3D_FEATURE_LEVEL featureLevel)
{
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0: return D3D11_COMMONSHADER_TEXEL_OFFSET_MAX_POSITIVE;
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return D3D11_COMMONSHADER_TEXEL_OFFSET_MAX_POSITIVE;
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return D3D11_COMMONSHADER_TEXEL_OFFSET_MAX_POSITIVE;
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return D3D11_COMMONSHADER_TEXEL_OFFSET_MAX_POSITIVE;
- // Sampling functions with offsets are not available below shader model 4.0.
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1: return 0;
+ // Sampling functions with offsets are not available below shader model 4.0.
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return 0;
- default: UNREACHABLE(); return 0;
+ default:
+ UNREACHABLE();
+ return 0;
}
}
-static size_t GetMaximumConstantBufferSize(D3D_FEATURE_LEVEL featureLevel)
+size_t GetMaximumConstantBufferSize(D3D_FEATURE_LEVEL featureLevel)
{
- // Returns a size_t despite the limit being a GLuint64 because size_t is the maximum size of
+ // Returns a size_t despite the limit being a GLuint64 because size_t is the maximum
+ // size of
// any buffer that could be allocated.
const size_t bytesPerComponent = 4 * sizeof(float);
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0: return D3D11_REQ_CONSTANT_BUFFER_ELEMENT_COUNT * bytesPerComponent;
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return D3D11_REQ_CONSTANT_BUFFER_ELEMENT_COUNT * bytesPerComponent;
+
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return D3D10_REQ_CONSTANT_BUFFER_ELEMENT_COUNT * bytesPerComponent;
+
+ // Limits from http://msdn.microsoft.com/en-us/library/windows/desktop/ff476501.aspx
+ // remarks section
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return 4096 * bytesPerComponent;
+
+ default:
+ UNREACHABLE();
+ return 0;
+ }
+}
+
+size_t GetMaximumStreamOutputBuffers(D3D_FEATURE_LEVEL featureLevel)
+{
+ switch (featureLevel)
+ {
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return D3D11_SO_BUFFER_SLOT_COUNT;
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return D3D10_REQ_CONSTANT_BUFFER_ELEMENT_COUNT * bytesPerComponent;
+ case D3D_FEATURE_LEVEL_10_1:
+ return D3D10_1_SO_BUFFER_SLOT_COUNT;
+ case D3D_FEATURE_LEVEL_10_0:
+ return D3D10_SO_BUFFER_SLOT_COUNT;
+
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return 0;
- // Limits from http://msdn.microsoft.com/en-us/library/windows/desktop/ff476501.aspx remarks section
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1: return 4096 * bytesPerComponent;
+ default:
+ UNREACHABLE();
+ return 0;
+ }
+}
+
+size_t GetMaximumStreamOutputInterleavedComponents(D3D_FEATURE_LEVEL featureLevel)
+{
+ switch (featureLevel)
+ {
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return GetMaximumVertexOutputVectors(featureLevel) * 4;
+
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return 0;
- default: UNREACHABLE(); return 0;
+ default:
+ UNREACHABLE();
+ return 0;
}
}
-static size_t GetMaximumStreamOutputBuffers(D3D_FEATURE_LEVEL featureLevel)
+size_t GetMaximumStreamOutputSeparateComponents(D3D_FEATURE_LEVEL featureLevel)
{
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0: return D3D11_SO_BUFFER_SLOT_COUNT;
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return GetMaximumStreamOutputInterleavedComponents(featureLevel) /
+ GetMaximumStreamOutputBuffers(featureLevel);
- case D3D_FEATURE_LEVEL_10_1: return D3D10_1_SO_BUFFER_SLOT_COUNT;
- case D3D_FEATURE_LEVEL_10_0: return D3D10_SO_BUFFER_SLOT_COUNT;
+ // D3D 10 and 10.1 only allow one output per output slot if an output slot other
+ // than zero is used.
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return 4;
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1: return 0;
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return 0;
- default: UNREACHABLE(); return 0;
+ default:
+ UNREACHABLE();
+ return 0;
+ }
+}
+
+size_t GetMaximumRenderToBufferWindowSize(D3D_FEATURE_LEVEL featureLevel)
+{
+ switch (featureLevel)
+ {
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return D3D11_REQ_RENDER_TO_BUFFER_WINDOW_WIDTH;
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return D3D10_REQ_RENDER_TO_BUFFER_WINDOW_WIDTH;
+
+ // REQ_RENDER_TO_BUFFER_WINDOW_WIDTH not supported on D3D11 Feature Level 9,
+ // use the maximum texture sizes
+ case D3D_FEATURE_LEVEL_9_3:
+ return D3D_FL9_3_REQ_TEXTURE2D_U_OR_V_DIMENSION;
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return D3D_FL9_1_REQ_TEXTURE2D_U_OR_V_DIMENSION;
+
+ default:
+ UNREACHABLE();
+ return 0;
}
}
-static size_t GetMaximumStreamOutputInterleavedComponents(D3D_FEATURE_LEVEL featureLevel)
+IntelDriverVersion GetIntelDriverVersion(const Optional<LARGE_INTEGER> driverVersion)
+{
+ if (!driverVersion.valid())
+ return IntelDriverVersion(0);
+
+ // According to http://www.intel.com/content/www/us/en/support/graphics-drivers/000005654.html,
+ // only the fourth part is necessary since it stands for the driver specific unique version
+ // number.
+ WORD part = LOWORD(driverVersion.value().LowPart);
+ return IntelDriverVersion(part);
+}
+
+} // anonymous namespace
+
+unsigned int GetReservedVertexUniformVectors(D3D_FEATURE_LEVEL featureLevel)
{
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0:
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return 0;
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return GetMaximumVertexOutputVectors(featureLevel) * 4;
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return 3; // dx_ViewAdjust, dx_ViewCoords and dx_ViewScale
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1: return 0;
+ default:
+ UNREACHABLE();
+ return 0;
+ }
+}
+
+unsigned int GetReservedFragmentUniformVectors(D3D_FEATURE_LEVEL featureLevel)
+{
+ switch (featureLevel)
+ {
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return 0;
+
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return 3;
- default: UNREACHABLE(); return 0;
+ default:
+ UNREACHABLE();
+ return 0;
}
}
-static size_t GetMaximumStreamOutputSeparateComponents(D3D_FEATURE_LEVEL featureLevel)
+gl::Version GetMaximumClientVersion(D3D_FEATURE_LEVEL featureLevel)
{
switch (featureLevel)
{
- case D3D_FEATURE_LEVEL_11_1:
- case D3D_FEATURE_LEVEL_11_0: return GetMaximumStreamOutputInterleavedComponents(featureLevel) /
- GetMaximumStreamOutputBuffers(featureLevel);
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return gl::Version(3, 1);
+ case D3D_FEATURE_LEVEL_10_1:
+ return gl::Version(3, 0);
+ case D3D_FEATURE_LEVEL_10_0:
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return gl::Version(2, 0);
- // D3D 10 and 10.1 only allow one output per output slot if an output slot other than zero is used.
- case D3D_FEATURE_LEVEL_10_1:
- case D3D_FEATURE_LEVEL_10_0: return 4;
+ default:
+ UNREACHABLE();
+ return gl::Version(0, 0);
+ }
+}
+
+unsigned int GetMaxViewportAndScissorRectanglesPerPipeline(D3D_FEATURE_LEVEL featureLevel)
+{
+ switch (featureLevel)
+ {
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return D3D11_VIEWPORT_AND_SCISSORRECT_OBJECT_COUNT_PER_PIPELINE;
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return 1;
+ default:
+ UNREACHABLE();
+ return 0;
+ }
+}
- case D3D_FEATURE_LEVEL_9_3:
- case D3D_FEATURE_LEVEL_9_2:
- case D3D_FEATURE_LEVEL_9_1: return 0;
+bool IsMultiviewSupported(D3D_FEATURE_LEVEL featureLevel)
+{
+ // The ANGLE_multiview extension can always be supported in D3D11 through geometry shaders.
+ switch (featureLevel)
+ {
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ return true;
+ default:
+ return false;
+ }
+}
- default: UNREACHABLE(); return 0;
+unsigned int GetMaxSampleMaskWords(D3D_FEATURE_LEVEL featureLevel)
+{
+ switch (featureLevel)
+ {
+ // D3D10+ only allows 1 sample mask.
+ case D3D_FEATURE_LEVEL_11_1:
+ case D3D_FEATURE_LEVEL_11_0:
+ case D3D_FEATURE_LEVEL_10_1:
+ case D3D_FEATURE_LEVEL_10_0:
+ return 1u;
+ case D3D_FEATURE_LEVEL_9_3:
+ case D3D_FEATURE_LEVEL_9_2:
+ case D3D_FEATURE_LEVEL_9_1:
+ return 0u;
+ default:
+ UNREACHABLE();
+ return 0u;
}
}
void GenerateCaps(ID3D11Device *device, ID3D11DeviceContext *deviceContext, const Renderer11DeviceCaps &renderer11DeviceCaps, gl::Caps *caps,
gl::TextureCapsMap *textureCapsMap, gl::Extensions *extensions, gl::Limitations *limitations)
{
- GLuint maxSamples = 0;
D3D_FEATURE_LEVEL featureLevel = renderer11DeviceCaps.featureLevel;
const gl::FormatSet &allFormats = gl::GetAllSizedInternalFormats();
- for (gl::FormatSet::const_iterator internalFormat = allFormats.begin(); internalFormat != allFormats.end(); ++internalFormat)
+ for (GLenum internalFormat : allFormats)
{
- gl::TextureCaps textureCaps = GenerateTextureFormatCaps(GetMaximumClientVersion(featureLevel), *internalFormat, device, renderer11DeviceCaps);
- textureCapsMap->insert(*internalFormat, textureCaps);
+ gl::TextureCaps textureCaps = GenerateTextureFormatCaps(
+ GetMaximumClientVersion(featureLevel), internalFormat, device, renderer11DeviceCaps);
+ textureCapsMap->insert(internalFormat, textureCaps);
- maxSamples = std::max(maxSamples, textureCaps.getMaxSamples());
-
- if (gl::GetInternalFormatInfo(*internalFormat).compressed)
+ if (gl::GetSizedInternalFormatInfo(internalFormat).compressed)
{
- caps->compressedTextureFormats.push_back(*internalFormat);
+ caps->compressedTextureFormats.push_back(internalFormat);
}
}
@@ -1226,6 +1346,14 @@ void GenerateCaps(ID3D11Device *device, ID3D11DeviceContext *deviceContext, cons
caps->maxVertexTextureImageUnits =
static_cast<GLuint>(GetMaximumVertexTextureUnits(featureLevel));
+ // Vertex Attribute Bindings are emulated on D3D11.
+ caps->maxVertexAttribBindings = caps->maxVertexAttributes;
+ // Experimental testing confirmed there is no explicit limit on maximum buffer offset in D3D11.
+ caps->maxVertexAttribRelativeOffset = std::numeric_limits<GLint>::max();
+ // Experimental testing confirmed 2048 is the maximum stride that D3D11 can support on all
+ // platforms.
+ caps->maxVertexAttribStride = 2048;
+
// Fragment shader limits
caps->maxFragmentUniformComponents =
static_cast<GLuint>(GetMaximumPixelUniformVectors(featureLevel)) * 4;
@@ -1239,10 +1367,28 @@ void GenerateCaps(ID3D11Device *device, ID3D11DeviceContext *deviceContext, cons
caps->minProgramTexelOffset = GetMinimumTexelOffset(featureLevel);
caps->maxProgramTexelOffset = GetMaximumTexelOffset(featureLevel);
+ // Compute shader limits
+ caps->maxComputeWorkGroupCount = GetMaxComputeWorkGroupCount(featureLevel);
+ caps->maxComputeWorkGroupSize = GetMaxComputeWorkGroupSize(featureLevel);
+ caps->maxComputeWorkGroupInvocations =
+ static_cast<GLuint>(GetMaxComputeWorkGroupInvocations(featureLevel));
+ caps->maxComputeUniformComponents =
+ static_cast<GLuint>(GetMaximumComputeUniformVectors(featureLevel)) * 4;
+ caps->maxComputeUniformBlocks =
+ static_cast<GLuint>(GetMaximumComputeUniformBlocks(featureLevel));
+ caps->maxComputeTextureImageUnits =
+ static_cast<GLuint>(GetMaximumComputeTextureUnits(featureLevel));
+ caps->maxImageUnits = static_cast<GLuint>(GetMaximumImageUnits(featureLevel));
+ caps->maxComputeImageUniforms =
+ static_cast<GLuint>(GetMaximumComputeImageUniforms(featureLevel));
+
// Aggregate shader limits
caps->maxUniformBufferBindings = caps->maxVertexUniformBlocks + caps->maxFragmentUniformBlocks;
caps->maxUniformBlockSize = GetMaximumConstantBufferSize(featureLevel);
+ // TODO(oetuaho): Get a more accurate limit. For now using the minimum requirement for GLES 3.1.
+ caps->maxUniformLocations = 1024;
+
// With DirectX 11.1, constant buffer offset and size must be a multiple of 16 constants of 16 bytes each.
// https://msdn.microsoft.com/en-us/library/windows/desktop/hh404649%28v=vs.85%29.aspx
// With DirectX 11.0, we emulate UBO offsets using copies of ranges of the UBO however
@@ -1254,6 +1400,9 @@ void GenerateCaps(ID3D11Device *device, ID3D11DeviceContext *deviceContext, cons
static_cast<GLint64>(caps->maxVertexUniformComponents);
caps->maxCombinedFragmentUniformComponents = (static_cast<GLint64>(caps->maxFragmentUniformBlocks) * static_cast<GLint64>(caps->maxUniformBlockSize / 4)) +
static_cast<GLint64>(caps->maxFragmentUniformComponents);
+ caps->maxCombinedComputeUniformComponents =
+ static_cast<GLuint>(caps->maxComputeUniformBlocks * (caps->maxUniformBlockSize / 4) +
+ caps->maxComputeUniformComponents);
caps->maxVaryingComponents =
static_cast<GLuint>(GetMaximumVertexOutputVectors(featureLevel)) * 4;
caps->maxVaryingVectors = static_cast<GLuint>(GetMaximumVertexOutputVectors(featureLevel));
@@ -1267,8 +1416,21 @@ void GenerateCaps(ID3D11Device *device, ID3D11DeviceContext *deviceContext, cons
caps->maxTransformFeedbackSeparateComponents =
static_cast<GLuint>(GetMaximumStreamOutputSeparateComponents(featureLevel));
- // Multisample limits
- caps->maxSamples = maxSamples;
+ // Defer the computation of multisample limits to Context::updateCaps() where max*Samples values
+ // are determined according to available sample counts for each individual format.
+ caps->maxSamples = std::numeric_limits<GLint>::max();
+ caps->maxColorTextureSamples = std::numeric_limits<GLint>::max();
+ caps->maxDepthTextureSamples = std::numeric_limits<GLint>::max();
+ caps->maxIntegerSamples = std::numeric_limits<GLint>::max();
+
+ // Sample mask words limits
+ caps->maxSampleMaskWords = GetMaxSampleMaskWords(featureLevel);
+
+ // Framebuffer limits
+ caps->maxFramebufferSamples = std::numeric_limits<GLint>::max();
+ caps->maxFramebufferWidth =
+ static_cast<GLuint>(GetMaximumRenderToBufferWindowSize(featureLevel));
+ caps->maxFramebufferHeight = caps->maxFramebufferWidth;
// GL extension support
extensions->setTextureExtensionSupport(*textureCapsMap);
@@ -1286,12 +1448,15 @@ void GenerateCaps(ID3D11Device *device, ID3D11DeviceContext *deviceContext, cons
extensions->maxTextureAnisotropy = GetMaximumAnisotropy(featureLevel);
extensions->occlusionQueryBoolean = GetOcclusionQuerySupport(featureLevel);
extensions->fence = GetEventQuerySupport(featureLevel);
- extensions->timerQuery = false; // Unimplemented
extensions->disjointTimerQuery = true;
extensions->queryCounterBitsTimeElapsed = 64;
extensions->queryCounterBitsTimestamp =
0; // Timestamps cannot be supported due to D3D11 limitations
extensions->robustness = true;
+ // Direct3D guarantees to return zero for any resource that is accessed out of bounds.
+ // See https://msdn.microsoft.com/en-us/library/windows/desktop/ff476332(v=vs.85).aspx
+ // and https://msdn.microsoft.com/en-us/library/windows/desktop/ff476900(v=vs.85).aspx
+ extensions->robustBufferAccessBehavior = true;
extensions->blendMinMax = true;
extensions->framebufferBlit = GetFramebufferBlitSupport(featureLevel);
extensions->framebufferMultisample = GetFramebufferMultisampleSupport(featureLevel);
@@ -1300,17 +1465,29 @@ void GenerateCaps(ID3D11Device *device, ID3D11DeviceContext *deviceContext, cons
extensions->standardDerivatives = GetDerivativeInstructionSupport(featureLevel);
extensions->shaderTextureLOD = GetShaderTextureLODSupport(featureLevel);
extensions->fragDepth = true;
+ extensions->multiview = IsMultiviewSupported(featureLevel);
+ if (extensions->multiview)
+ {
+ extensions->maxViews =
+ std::min(static_cast<GLuint>(gl::IMPLEMENTATION_ANGLE_MULTIVIEW_MAX_VIEWS),
+ std::min(static_cast<GLuint>(GetMaximum2DTextureArraySize(featureLevel)),
+ GetMaxViewportAndScissorRectanglesPerPipeline(featureLevel)));
+ }
extensions->textureUsage = true; // This could be false since it has no effect in D3D11
extensions->discardFramebuffer = true;
extensions->translatedShaderSource = true;
extensions->fboRenderMipmap = false;
extensions->debugMarker = true;
extensions->eglImage = true;
+ extensions->eglImageExternal = true;
+ extensions->eglImageExternalEssl3 = true;
+ extensions->eglStreamConsumerExternal = true;
extensions->unpackSubimage = true;
extensions->packSubimage = true;
- extensions->vertexArrayObject = true;
- extensions->noError = true;
extensions->lossyETCDecode = true;
+ extensions->syncQuery = GetEventQuerySupport(featureLevel);
+ extensions->copyTexture = true;
+ extensions->copyCompressedTexture = true;
// D3D11 Feature Level 10_0+ uses SV_IsFrontFace in HLSL to emulate gl_FrontFacing.
// D3D11 Feature Level 9_3 doesn't support SV_IsFrontFace, and has no equivalent, so can't support gl_FrontFacing.
@@ -1340,8 +1517,355 @@ void GenerateCaps(ID3D11Device *device, ID3D11DeviceContext *deviceContext, cons
#endif
}
+void GetSamplePosition(GLsizei sampleCount, size_t index, GLfloat *xy)
+{
+ size_t indexKey = static_cast<size_t>(ceil(log(sampleCount)));
+ ASSERT(indexKey < kSamplePositions.size() &&
+ (2 * index + 1) < kSamplePositions[indexKey].size());
+
+ xy[0] = kSamplePositions[indexKey][2 * index];
+ xy[1] = kSamplePositions[indexKey][2 * index + 1];
+}
+
} // namespace d3d11_gl
+namespace gl_d3d11
+{
+
+D3D11_BLEND ConvertBlendFunc(GLenum glBlend, bool isAlpha)
+{
+ D3D11_BLEND d3dBlend = D3D11_BLEND_ZERO;
+
+ switch (glBlend)
+ {
+ case GL_ZERO:
+ d3dBlend = D3D11_BLEND_ZERO;
+ break;
+ case GL_ONE:
+ d3dBlend = D3D11_BLEND_ONE;
+ break;
+ case GL_SRC_COLOR:
+ d3dBlend = (isAlpha ? D3D11_BLEND_SRC_ALPHA : D3D11_BLEND_SRC_COLOR);
+ break;
+ case GL_ONE_MINUS_SRC_COLOR:
+ d3dBlend = (isAlpha ? D3D11_BLEND_INV_SRC_ALPHA : D3D11_BLEND_INV_SRC_COLOR);
+ break;
+ case GL_DST_COLOR:
+ d3dBlend = (isAlpha ? D3D11_BLEND_DEST_ALPHA : D3D11_BLEND_DEST_COLOR);
+ break;
+ case GL_ONE_MINUS_DST_COLOR:
+ d3dBlend = (isAlpha ? D3D11_BLEND_INV_DEST_ALPHA : D3D11_BLEND_INV_DEST_COLOR);
+ break;
+ case GL_SRC_ALPHA:
+ d3dBlend = D3D11_BLEND_SRC_ALPHA;
+ break;
+ case GL_ONE_MINUS_SRC_ALPHA:
+ d3dBlend = D3D11_BLEND_INV_SRC_ALPHA;
+ break;
+ case GL_DST_ALPHA:
+ d3dBlend = D3D11_BLEND_DEST_ALPHA;
+ break;
+ case GL_ONE_MINUS_DST_ALPHA:
+ d3dBlend = D3D11_BLEND_INV_DEST_ALPHA;
+ break;
+ case GL_CONSTANT_COLOR:
+ d3dBlend = D3D11_BLEND_BLEND_FACTOR;
+ break;
+ case GL_ONE_MINUS_CONSTANT_COLOR:
+ d3dBlend = D3D11_BLEND_INV_BLEND_FACTOR;
+ break;
+ case GL_CONSTANT_ALPHA:
+ d3dBlend = D3D11_BLEND_BLEND_FACTOR;
+ break;
+ case GL_ONE_MINUS_CONSTANT_ALPHA:
+ d3dBlend = D3D11_BLEND_INV_BLEND_FACTOR;
+ break;
+ case GL_SRC_ALPHA_SATURATE:
+ d3dBlend = D3D11_BLEND_SRC_ALPHA_SAT;
+ break;
+ default:
+ UNREACHABLE();
+ }
+
+ return d3dBlend;
+}
+
+D3D11_BLEND_OP ConvertBlendOp(GLenum glBlendOp)
+{
+ D3D11_BLEND_OP d3dBlendOp = D3D11_BLEND_OP_ADD;
+
+ switch (glBlendOp)
+ {
+ case GL_FUNC_ADD:
+ d3dBlendOp = D3D11_BLEND_OP_ADD;
+ break;
+ case GL_FUNC_SUBTRACT:
+ d3dBlendOp = D3D11_BLEND_OP_SUBTRACT;
+ break;
+ case GL_FUNC_REVERSE_SUBTRACT:
+ d3dBlendOp = D3D11_BLEND_OP_REV_SUBTRACT;
+ break;
+ case GL_MIN:
+ d3dBlendOp = D3D11_BLEND_OP_MIN;
+ break;
+ case GL_MAX:
+ d3dBlendOp = D3D11_BLEND_OP_MAX;
+ break;
+ default:
+ UNREACHABLE();
+ }
+
+ return d3dBlendOp;
+}
+
+UINT8 ConvertColorMask(bool red, bool green, bool blue, bool alpha)
+{
+ UINT8 mask = 0;
+ if (red)
+ {
+ mask |= D3D11_COLOR_WRITE_ENABLE_RED;
+ }
+ if (green)
+ {
+ mask |= D3D11_COLOR_WRITE_ENABLE_GREEN;
+ }
+ if (blue)
+ {
+ mask |= D3D11_COLOR_WRITE_ENABLE_BLUE;
+ }
+ if (alpha)
+ {
+ mask |= D3D11_COLOR_WRITE_ENABLE_ALPHA;
+ }
+ return mask;
+}
+
+D3D11_CULL_MODE ConvertCullMode(bool cullEnabled, gl::CullFaceMode cullMode)
+{
+ D3D11_CULL_MODE cull = D3D11_CULL_NONE;
+
+ if (cullEnabled)
+ {
+ switch (cullMode)
+ {
+ case gl::CullFaceMode::Front:
+ cull = D3D11_CULL_FRONT;
+ break;
+ case gl::CullFaceMode::Back:
+ cull = D3D11_CULL_BACK;
+ break;
+ case gl::CullFaceMode::FrontAndBack:
+ cull = D3D11_CULL_NONE;
+ break;
+ default:
+ UNREACHABLE();
+ }
+ }
+ else
+ {
+ cull = D3D11_CULL_NONE;
+ }
+
+ return cull;
+}
+
+D3D11_COMPARISON_FUNC ConvertComparison(GLenum comparison)
+{
+ D3D11_COMPARISON_FUNC d3dComp = D3D11_COMPARISON_NEVER;
+ switch (comparison)
+ {
+ case GL_NEVER:
+ d3dComp = D3D11_COMPARISON_NEVER;
+ break;
+ case GL_ALWAYS:
+ d3dComp = D3D11_COMPARISON_ALWAYS;
+ break;
+ case GL_LESS:
+ d3dComp = D3D11_COMPARISON_LESS;
+ break;
+ case GL_LEQUAL:
+ d3dComp = D3D11_COMPARISON_LESS_EQUAL;
+ break;
+ case GL_EQUAL:
+ d3dComp = D3D11_COMPARISON_EQUAL;
+ break;
+ case GL_GREATER:
+ d3dComp = D3D11_COMPARISON_GREATER;
+ break;
+ case GL_GEQUAL:
+ d3dComp = D3D11_COMPARISON_GREATER_EQUAL;
+ break;
+ case GL_NOTEQUAL:
+ d3dComp = D3D11_COMPARISON_NOT_EQUAL;
+ break;
+ default:
+ UNREACHABLE();
+ }
+
+ return d3dComp;
+}
+
+D3D11_DEPTH_WRITE_MASK ConvertDepthMask(bool depthWriteEnabled)
+{
+ return depthWriteEnabled ? D3D11_DEPTH_WRITE_MASK_ALL : D3D11_DEPTH_WRITE_MASK_ZERO;
+}
+
+UINT8 ConvertStencilMask(GLuint stencilmask)
+{
+ return static_cast<UINT8>(stencilmask);
+}
+
+D3D11_STENCIL_OP ConvertStencilOp(GLenum stencilOp)
+{
+ D3D11_STENCIL_OP d3dStencilOp = D3D11_STENCIL_OP_KEEP;
+
+ switch (stencilOp)
+ {
+ case GL_ZERO:
+ d3dStencilOp = D3D11_STENCIL_OP_ZERO;
+ break;
+ case GL_KEEP:
+ d3dStencilOp = D3D11_STENCIL_OP_KEEP;
+ break;
+ case GL_REPLACE:
+ d3dStencilOp = D3D11_STENCIL_OP_REPLACE;
+ break;
+ case GL_INCR:
+ d3dStencilOp = D3D11_STENCIL_OP_INCR_SAT;
+ break;
+ case GL_DECR:
+ d3dStencilOp = D3D11_STENCIL_OP_DECR_SAT;
+ break;
+ case GL_INVERT:
+ d3dStencilOp = D3D11_STENCIL_OP_INVERT;
+ break;
+ case GL_INCR_WRAP:
+ d3dStencilOp = D3D11_STENCIL_OP_INCR;
+ break;
+ case GL_DECR_WRAP:
+ d3dStencilOp = D3D11_STENCIL_OP_DECR;
+ break;
+ default:
+ UNREACHABLE();
+ }
+
+ return d3dStencilOp;
+}
+
+D3D11_FILTER ConvertFilter(GLenum minFilter,
+ GLenum magFilter,
+ float maxAnisotropy,
+ GLenum comparisonMode)
+{
+ bool comparison = comparisonMode != GL_NONE;
+
+ if (maxAnisotropy > 1.0f)
+ {
+ return D3D11_ENCODE_ANISOTROPIC_FILTER(static_cast<D3D11_COMPARISON_FUNC>(comparison));
+ }
+ else
+ {
+ D3D11_FILTER_TYPE dxMin = D3D11_FILTER_TYPE_POINT;
+ D3D11_FILTER_TYPE dxMip = D3D11_FILTER_TYPE_POINT;
+ switch (minFilter)
+ {
+ case GL_NEAREST:
+ dxMin = D3D11_FILTER_TYPE_POINT;
+ dxMip = D3D11_FILTER_TYPE_POINT;
+ break;
+ case GL_LINEAR:
+ dxMin = D3D11_FILTER_TYPE_LINEAR;
+ dxMip = D3D11_FILTER_TYPE_POINT;
+ break;
+ case GL_NEAREST_MIPMAP_NEAREST:
+ dxMin = D3D11_FILTER_TYPE_POINT;
+ dxMip = D3D11_FILTER_TYPE_POINT;
+ break;
+ case GL_LINEAR_MIPMAP_NEAREST:
+ dxMin = D3D11_FILTER_TYPE_LINEAR;
+ dxMip = D3D11_FILTER_TYPE_POINT;
+ break;
+ case GL_NEAREST_MIPMAP_LINEAR:
+ dxMin = D3D11_FILTER_TYPE_POINT;
+ dxMip = D3D11_FILTER_TYPE_LINEAR;
+ break;
+ case GL_LINEAR_MIPMAP_LINEAR:
+ dxMin = D3D11_FILTER_TYPE_LINEAR;
+ dxMip = D3D11_FILTER_TYPE_LINEAR;
+ break;
+ default:
+ UNREACHABLE();
+ }
+
+ D3D11_FILTER_TYPE dxMag = D3D11_FILTER_TYPE_POINT;
+ switch (magFilter)
+ {
+ case GL_NEAREST:
+ dxMag = D3D11_FILTER_TYPE_POINT;
+ break;
+ case GL_LINEAR:
+ dxMag = D3D11_FILTER_TYPE_LINEAR;
+ break;
+ default:
+ UNREACHABLE();
+ }
+
+ return D3D11_ENCODE_BASIC_FILTER(dxMin, dxMag, dxMip,
+ static_cast<D3D11_COMPARISON_FUNC>(comparison));
+ }
+}
+
+D3D11_TEXTURE_ADDRESS_MODE ConvertTextureWrap(GLenum wrap)
+{
+ switch (wrap)
+ {
+ case GL_REPEAT:
+ return D3D11_TEXTURE_ADDRESS_WRAP;
+ case GL_CLAMP_TO_EDGE:
+ return D3D11_TEXTURE_ADDRESS_CLAMP;
+ case GL_MIRRORED_REPEAT:
+ return D3D11_TEXTURE_ADDRESS_MIRROR;
+ default:
+ UNREACHABLE();
+ }
+
+ return D3D11_TEXTURE_ADDRESS_WRAP;
+}
+
+UINT ConvertMaxAnisotropy(float maxAnisotropy, D3D_FEATURE_LEVEL featureLevel)
+{
+ return static_cast<UINT>(std::min(maxAnisotropy, d3d11_gl::GetMaximumAnisotropy(featureLevel)));
+}
+
+D3D11_QUERY ConvertQueryType(GLenum queryType)
+{
+ switch (queryType)
+ {
+ case GL_ANY_SAMPLES_PASSED_EXT:
+ case GL_ANY_SAMPLES_PASSED_CONSERVATIVE_EXT:
+ return D3D11_QUERY_OCCLUSION;
+ case GL_TRANSFORM_FEEDBACK_PRIMITIVES_WRITTEN:
+ return D3D11_QUERY_SO_STATISTICS;
+ case GL_TIME_ELAPSED_EXT:
+ // Two internal queries are also created for begin/end timestamps
+ return D3D11_QUERY_TIMESTAMP_DISJOINT;
+ case GL_COMMANDS_COMPLETED_CHROMIUM:
+ return D3D11_QUERY_EVENT;
+ default:
+ UNREACHABLE();
+ return D3D11_QUERY_EVENT;
+ }
+}
+
+// Get the D3D11 write mask covering all color channels of a given format
+UINT8 GetColorMask(const gl::InternalFormat &format)
+{
+ return ConvertColorMask(format.redBits > 0, format.greenBits > 0, format.blueBits > 0,
+ format.alphaBits > 0);
+}
+
+} // namespace gl_d3d11
+
namespace d3d11
{
@@ -1352,9 +1876,7 @@ ANGLED3D11DeviceType GetDeviceType(ID3D11Device *device)
IDXGIDevice *dxgiDevice = nullptr;
IDXGIAdapter *dxgiAdapter = nullptr;
-#if defined(ANGLE_ENABLE_D3D11_1)
IDXGIAdapter2 *dxgiAdapter2 = nullptr;
-#endif
ANGLED3D11DeviceType retDeviceType = ANGLE_D3D11_DEVICE_TYPE_UNKNOWN;
@@ -1365,7 +1887,6 @@ ANGLED3D11DeviceType GetDeviceType(ID3D11Device *device)
if (SUCCEEDED(hr))
{
std::wstring adapterString;
-#if defined(ANGLE_ENABLE_D3D11_1)
HRESULT adapter2hr =
dxgiAdapter->QueryInterface(__uuidof(dxgiAdapter2), (void **)&dxgiAdapter2);
if (SUCCEEDED(adapter2hr))
@@ -1378,7 +1899,6 @@ ANGLED3D11DeviceType GetDeviceType(ID3D11Device *device)
adapterString = std::wstring(adapterDesc2.Description);
}
else
-#endif
{
DXGI_ADAPTER_DESC adapterDesc;
dxgiAdapter->GetDesc(&adapterDesc);
@@ -1410,16 +1930,14 @@ ANGLED3D11DeviceType GetDeviceType(ID3D11Device *device)
SafeRelease(dxgiDevice);
SafeRelease(dxgiAdapter);
-#if defined(ANGLE_ENABLE_D3D11_1)
SafeRelease(dxgiAdapter2);
-#endif
return retDeviceType;
}
void MakeValidSize(bool isImage, DXGI_FORMAT format, GLsizei *requestWidth, GLsizei *requestHeight, int *levelOffset)
{
- const DXGIFormat &dxgiFormatInfo = d3d11::GetDXGIFormatInfo(format);
+ const DXGIFormatSize &dxgiFormatInfo = d3d11::GetDXGIFormatSizeInfo(format);
int upsampleCount = 0;
// Don't expand the size of full textures that are at least (blockWidth x blockHeight) already.
@@ -1433,7 +1951,10 @@ void MakeValidSize(bool isImage, DXGI_FORMAT format, GLsizei *requestWidth, GLsi
upsampleCount++;
}
}
- *levelOffset = upsampleCount;
+ if (levelOffset)
+ {
+ *levelOffset = upsampleCount;
+ }
}
void GenerateInitialTextureData(GLint internalFormat,
@@ -1445,10 +1966,11 @@ void GenerateInitialTextureData(GLint internalFormat,
std::vector<D3D11_SUBRESOURCE_DATA> *outSubresourceData,
std::vector<std::vector<BYTE>> *outData)
{
- const d3d11::TextureFormat &d3dFormatInfo = d3d11::GetTextureFormatInfo(internalFormat, renderer11DeviceCaps);
- ASSERT(d3dFormatInfo.dataInitializerFunction != NULL);
+ const d3d11::Format &d3dFormatInfo = d3d11::Format::Get(internalFormat, renderer11DeviceCaps);
+ ASSERT(d3dFormatInfo.dataInitializerFunction != nullptr);
- const d3d11::DXGIFormat &dxgiFormatInfo = d3d11::GetDXGIFormatInfo(d3dFormatInfo.texFormat);
+ const d3d11::DXGIFormatSize &dxgiFormatInfo =
+ d3d11::GetDXGIFormatSizeInfo(d3dFormatInfo.texFormat);
outSubresourceData->resize(mipLevels);
outData->resize(mipLevels);
@@ -1495,6 +2017,36 @@ void SetPositionLayerTexCoord3DVertex(PositionLayerTexCoord3DVertex* vertex, flo
vertex->s = s;
}
+BlendStateKey::BlendStateKey()
+{
+ memset(this, 0, sizeof(BlendStateKey));
+}
+
+bool operator==(const BlendStateKey &a, const BlendStateKey &b)
+{
+ return memcmp(&a, &b, sizeof(BlendStateKey)) == 0;
+}
+
+bool operator!=(const BlendStateKey &a, const BlendStateKey &b)
+{
+ return !(a == b);
+}
+
+RasterizerStateKey::RasterizerStateKey()
+{
+ memset(this, 0, sizeof(RasterizerStateKey));
+}
+
+bool operator==(const RasterizerStateKey &a, const RasterizerStateKey &b)
+{
+ return memcmp(&a, &b, sizeof(RasterizerStateKey)) == 0;
+}
+
+bool operator!=(const RasterizerStateKey &a, const RasterizerStateKey &b)
+{
+ return !(a == b);
+}
+
HRESULT SetDebugName(ID3D11DeviceChild *resource, const char *name)
{
#if defined(_DEBUG)
@@ -1533,34 +2085,66 @@ HRESULT SetDebugName(ID3D11DeviceChild *resource, const char *name)
#endif
}
+// Keep this in cpp file where it has visibility of Renderer11.h, otherwise calling
+// allocateResource is only compatible with Clang and MSVS, which support calling a
+// method on a forward declared class in a template.
+template <ResourceType ResourceT>
+gl::Error LazyResource<ResourceT>::resolveImpl(Renderer11 *renderer,
+ const GetDescType<ResourceT> &desc,
+ GetInitDataType<ResourceT> *initData,
+ const char *name)
+{
+ if (!mResource.valid())
+ {
+ ANGLE_TRY(renderer->allocateResource(desc, initData, &mResource));
+ mResource.setDebugName(name);
+ }
+ return gl::NoError();
+}
+
+template gl::Error LazyResource<ResourceType::BlendState>::resolveImpl(Renderer11 *renderer,
+ const D3D11_BLEND_DESC &desc,
+ void *initData,
+ const char *name);
+template gl::Error LazyResource<ResourceType::ComputeShader>::resolveImpl(Renderer11 *renderer,
+ const ShaderData &desc,
+ void *initData,
+ const char *name);
+template gl::Error LazyResource<ResourceType::GeometryShader>::resolveImpl(
+ Renderer11 *renderer,
+ const ShaderData &desc,
+ const std::vector<D3D11_SO_DECLARATION_ENTRY> *initData,
+ const char *name);
+template gl::Error LazyResource<ResourceType::InputLayout>::resolveImpl(
+ Renderer11 *renderer,
+ const InputElementArray &desc,
+ const ShaderData *initData,
+ const char *name);
+template gl::Error LazyResource<ResourceType::PixelShader>::resolveImpl(Renderer11 *renderer,
+ const ShaderData &desc,
+ void *initData,
+ const char *name);
+template gl::Error LazyResource<ResourceType::VertexShader>::resolveImpl(Renderer11 *renderer,
+ const ShaderData &desc,
+ void *initData,
+ const char *name);
+
LazyInputLayout::LazyInputLayout(const D3D11_INPUT_ELEMENT_DESC *inputDesc,
size_t inputDescLen,
const BYTE *byteCode,
size_t byteCodeLen,
const char *debugName)
- : mInputDesc(inputDescLen),
- mByteCodeLen(byteCodeLen),
- mByteCode(byteCode),
- mDebugName(debugName)
+ : mInputDesc(inputDesc, inputDescLen), mByteCode(byteCode, byteCodeLen), mDebugName(debugName)
{
- memcpy(&mInputDesc[0], inputDesc, sizeof(D3D11_INPUT_ELEMENT_DESC) * inputDescLen);
}
-ID3D11InputLayout *LazyInputLayout::resolve(ID3D11Device *device)
+LazyInputLayout::~LazyInputLayout()
{
- checkAssociatedDevice(device);
-
- if (mResource == nullptr)
- {
- HRESULT result =
- device->CreateInputLayout(&mInputDesc[0], static_cast<UINT>(mInputDesc.size()),
- mByteCode, mByteCodeLen, &mResource);
- ASSERT(SUCCEEDED(result));
- UNUSED_ASSERTION_VARIABLE(result);
- d3d11::SetDebugName(mResource, mDebugName);
- }
+}
- return mResource;
+gl::Error LazyInputLayout::resolve(Renderer11 *renderer)
+{
+ return resolveImpl(renderer, mInputDesc, &mByteCode, mDebugName);
}
LazyBlendState::LazyBlendState(const D3D11_BLEND_DESC &desc, const char *debugName)
@@ -1568,213 +2152,270 @@ LazyBlendState::LazyBlendState(const D3D11_BLEND_DESC &desc, const char *debugNa
{
}
-ID3D11BlendState *LazyBlendState::resolve(ID3D11Device *device)
+gl::Error LazyBlendState::resolve(Renderer11 *renderer)
+{
+ return resolveImpl(renderer, mDesc, nullptr, mDebugName);
+}
+
+angle::WorkaroundsD3D GenerateWorkarounds(const Renderer11DeviceCaps &deviceCaps,
+ const DXGI_ADAPTER_DESC &adapterDesc)
{
- checkAssociatedDevice(device);
+ bool is9_3 = (deviceCaps.featureLevel <= D3D_FEATURE_LEVEL_9_3);
- if (mResource == nullptr)
+ angle::WorkaroundsD3D workarounds;
+ workarounds.mrtPerfWorkaround = true;
+ workarounds.setDataFasterThanImageUpload = true;
+ workarounds.zeroMaxLodWorkaround = is9_3;
+ workarounds.useInstancedPointSpriteEmulation = is9_3;
+
+ // TODO(jmadill): Narrow problematic driver range.
+ if (IsNvidia(adapterDesc.VendorId))
{
- HRESULT result = device->CreateBlendState(&mDesc, &mResource);
- ASSERT(SUCCEEDED(result));
- UNUSED_ASSERTION_VARIABLE(result);
- d3d11::SetDebugName(mResource, mDebugName);
+ if (deviceCaps.driverVersion.valid())
+ {
+ WORD part1 = HIWORD(deviceCaps.driverVersion.value().LowPart);
+ WORD part2 = LOWORD(deviceCaps.driverVersion.value().LowPart);
+
+ // Disable the workaround to fix a second driver bug on newer NVIDIA.
+ workarounds.depthStencilBlitExtraCopy = (part1 <= 13u && part2 < 6881);
+ }
+ else
+ {
+ workarounds.depthStencilBlitExtraCopy = true;
+ }
}
- return mResource;
+ // TODO(jmadill): Disable workaround when we have a fixed compiler DLL.
+ workarounds.expandIntegerPowExpressions = true;
+
+ workarounds.flushAfterEndingTransformFeedback = IsNvidia(adapterDesc.VendorId);
+ workarounds.getDimensionsIgnoresBaseLevel = IsNvidia(adapterDesc.VendorId);
+
+ if (IsIntel(adapterDesc.VendorId))
+ {
+ IntelDriverVersion capsVersion = d3d11_gl::GetIntelDriverVersion(deviceCaps.driverVersion);
+
+ workarounds.preAddTexelFetchOffsets = true;
+ workarounds.useSystemMemoryForConstantBuffers = true;
+ workarounds.disableB5G6R5Support = capsVersion < IntelDriverVersion(4539);
+ workarounds.addDummyTextureNoRenderTarget = capsVersion < IntelDriverVersion(4815);
+ if (IsSkylake(adapterDesc.DeviceId))
+ {
+ workarounds.callClearTwice = capsVersion < IntelDriverVersion(4771);
+ workarounds.emulateIsnanFloat = capsVersion < IntelDriverVersion(4542);
+ }
+ else if (IsBroadwell(adapterDesc.DeviceId) || IsHaswell(adapterDesc.DeviceId))
+ {
+ workarounds.rewriteUnaryMinusOperator = capsVersion < IntelDriverVersion(4624);
+ }
+ }
+
+ // TODO(jmadill): Disable when we have a fixed driver version.
+ workarounds.emulateTinyStencilTextures = IsAMD(adapterDesc.VendorId);
+
+ // The tiny stencil texture workaround involves using CopySubresource or UpdateSubresource on a
+ // depth stencil texture. This is not allowed until feature level 10.1 but since it is not
+ // possible to support ES3 on these devices, there is no need for the workaround to begin with
+ // (anglebug.com/1572).
+ if (deviceCaps.featureLevel < D3D_FEATURE_LEVEL_10_1)
+ {
+ workarounds.emulateTinyStencilTextures = false;
+ }
+
+ // If the VPAndRTArrayIndexFromAnyShaderFeedingRasterizer feature is not available, we have to
+ // select the viewport / RT array index in the geometry shader.
+ workarounds.selectViewInGeometryShader =
+ (deviceCaps.supportsVpRtIndexWriteFromVertexShader == false);
+
+ // Call platform hooks for testing overrides.
+ auto *platform = ANGLEPlatformCurrent();
+ platform->overrideWorkaroundsD3D(platform, &workarounds);
+
+ return workarounds;
}
-WorkaroundsD3D GenerateWorkarounds(D3D_FEATURE_LEVEL featureLevel)
+void InitConstantBufferDesc(D3D11_BUFFER_DESC *constantBufferDescription, size_t byteWidth)
{
- WorkaroundsD3D workarounds;
- workarounds.mrtPerfWorkaround = true;
- workarounds.setDataFasterThanImageUpload = true;
- workarounds.zeroMaxLodWorkaround = (featureLevel <= D3D_FEATURE_LEVEL_9_3);
- workarounds.useInstancedPointSpriteEmulation = (featureLevel <= D3D_FEATURE_LEVEL_9_3);
- return workarounds;
+ constantBufferDescription->ByteWidth = static_cast<UINT>(byteWidth);
+ constantBufferDescription->Usage = D3D11_USAGE_DYNAMIC;
+ constantBufferDescription->BindFlags = D3D11_BIND_CONSTANT_BUFFER;
+ constantBufferDescription->CPUAccessFlags = D3D11_CPU_ACCESS_WRITE;
+ constantBufferDescription->MiscFlags = 0;
+ constantBufferDescription->StructureByteStride = 0;
}
} // namespace d3d11
-TextureHelper11::TextureHelper11()
- : mTextureType(GL_NONE),
- mFormat(DXGI_FORMAT_UNKNOWN),
- mSampleCount(0),
- mTexture2D(nullptr),
- mTexture3D(nullptr)
+// TextureHelper11 implementation.
+TextureHelper11::TextureHelper11() : mFormatSet(nullptr), mSampleCount(0)
{
}
-TextureHelper11::TextureHelper11(TextureHelper11 &&toCopy)
- : mTextureType(toCopy.mTextureType),
- mExtents(toCopy.mExtents),
- mFormat(toCopy.mFormat),
- mSampleCount(toCopy.mSampleCount),
- mTexture2D(toCopy.mTexture2D),
- mTexture3D(toCopy.mTexture3D)
+TextureHelper11::TextureHelper11(TextureHelper11 &&toCopy) : TextureHelper11()
{
- toCopy.reset();
+ *this = std::move(toCopy);
}
-// static
-TextureHelper11 TextureHelper11::MakeAndReference(ID3D11Resource *genericResource)
+TextureHelper11::TextureHelper11(const TextureHelper11 &other)
+ : mFormatSet(other.mFormatSet), mExtents(other.mExtents), mSampleCount(other.mSampleCount)
{
- TextureHelper11 newHelper;
- newHelper.mTexture2D = d3d11::DynamicCastComObject<ID3D11Texture2D>(genericResource);
- newHelper.mTexture3D = d3d11::DynamicCastComObject<ID3D11Texture3D>(genericResource);
- newHelper.mTextureType = newHelper.mTexture2D ? GL_TEXTURE_2D : GL_TEXTURE_3D;
- newHelper.initDesc();
- return newHelper;
+ mData = other.mData;
}
-// static
-TextureHelper11 TextureHelper11::MakeAndPossess2D(ID3D11Texture2D *texToOwn)
+TextureHelper11::~TextureHelper11()
{
- TextureHelper11 newHelper;
- newHelper.mTexture2D = texToOwn;
- newHelper.mTextureType = GL_TEXTURE_2D;
- newHelper.initDesc();
- return newHelper;
}
-// static
-TextureHelper11 TextureHelper11::MakeAndPossess3D(ID3D11Texture3D *texToOwn)
+void TextureHelper11::getDesc(D3D11_TEXTURE2D_DESC *desc) const
{
- TextureHelper11 newHelper;
- newHelper.mTexture3D = texToOwn;
- newHelper.mTextureType = GL_TEXTURE_3D;
- newHelper.initDesc();
- return newHelper;
+ static_cast<ID3D11Texture2D *>(mData->object)->GetDesc(desc);
}
-void TextureHelper11::initDesc()
+void TextureHelper11::getDesc(D3D11_TEXTURE3D_DESC *desc) const
{
- if (mTextureType == GL_TEXTURE_2D)
- {
- ASSERT(!mTexture3D);
- D3D11_TEXTURE2D_DESC desc2D;
- mTexture2D->GetDesc(&desc2D);
+ static_cast<ID3D11Texture3D *>(mData->object)->GetDesc(desc);
+}
- mExtents.width = static_cast<int>(desc2D.Width);
- mExtents.height = static_cast<int>(desc2D.Height);
- mExtents.depth = 1;
- mFormat = desc2D.Format;
- mSampleCount = desc2D.SampleDesc.Count;
- }
- else
- {
- ASSERT(mTexture3D && mTextureType == GL_TEXTURE_3D);
- D3D11_TEXTURE3D_DESC desc3D;
- mTexture3D->GetDesc(&desc3D);
+void TextureHelper11::initDesc(const D3D11_TEXTURE2D_DESC &desc2D)
+{
+ mData->resourceType = ResourceType::Texture2D;
+ mExtents.width = static_cast<int>(desc2D.Width);
+ mExtents.height = static_cast<int>(desc2D.Height);
+ mExtents.depth = 1;
+ mSampleCount = desc2D.SampleDesc.Count;
+}
- mExtents.width = static_cast<int>(desc3D.Width);
- mExtents.height = static_cast<int>(desc3D.Height);
- mExtents.depth = static_cast<int>(desc3D.Depth);
- mFormat = desc3D.Format;
- mSampleCount = 1;
- }
+void TextureHelper11::initDesc(const D3D11_TEXTURE3D_DESC &desc3D)
+{
+ mData->resourceType = ResourceType::Texture3D;
+ mExtents.width = static_cast<int>(desc3D.Width);
+ mExtents.height = static_cast<int>(desc3D.Height);
+ mExtents.depth = static_cast<int>(desc3D.Depth);
+ mSampleCount = 1;
}
-TextureHelper11::~TextureHelper11()
+TextureHelper11 &TextureHelper11::operator=(TextureHelper11 &&other)
{
- SafeRelease(mTexture2D);
- SafeRelease(mTexture3D);
+ std::swap(mData, other.mData);
+ std::swap(mExtents, other.mExtents);
+ std::swap(mFormatSet, other.mFormatSet);
+ std::swap(mSampleCount, other.mSampleCount);
+ return *this;
}
-ID3D11Resource *TextureHelper11::getResource() const
+TextureHelper11 &TextureHelper11::operator=(const TextureHelper11 &other)
{
- return mTexture2D ? static_cast<ID3D11Resource *>(mTexture2D)
- : static_cast<ID3D11Resource *>(mTexture3D);
+ mData = other.mData;
+ mExtents = other.mExtents;
+ mFormatSet = other.mFormatSet;
+ mSampleCount = other.mSampleCount;
+ return *this;
}
-TextureHelper11 &TextureHelper11::operator=(TextureHelper11 &&texture)
+bool TextureHelper11::operator==(const TextureHelper11 &other) const
{
- SafeRelease(mTexture2D);
- SafeRelease(mTexture3D);
+ return mData->object == other.mData->object;
+}
- mTextureType = texture.mTextureType;
- mExtents = texture.mExtents;
- mFormat = texture.mFormat;
- mSampleCount = texture.mSampleCount;
- mTexture2D = texture.mTexture2D;
- mTexture3D = texture.mTexture3D;
- texture.reset();
- return *this;
+bool TextureHelper11::operator!=(const TextureHelper11 &other) const
+{
+ return mData->object != other.mData->object;
}
-void TextureHelper11::reset()
+bool UsePresentPathFast(const Renderer11 *renderer,
+ const gl::FramebufferAttachment *framebufferAttachment)
+{
+ if (framebufferAttachment == nullptr)
+ {
+ return false;
+ }
+
+ return (framebufferAttachment->type() == GL_FRAMEBUFFER_DEFAULT &&
+ renderer->presentPathFastEnabled());
+}
+
+bool UsePrimitiveRestartWorkaround(bool primitiveRestartFixedIndexEnabled, GLenum type)
{
- mTextureType = GL_NONE;
- mExtents = gl::Extents();
- mFormat = DXGI_FORMAT_UNKNOWN;
- mSampleCount = 0;
- mTexture2D = nullptr;
- mTexture3D = nullptr;
+ // We should never have to deal with primitive restart workaround issue with GL_UNSIGNED_INT
+ // indices, since we restrict it via MAX_ELEMENT_INDEX.
+ return (!primitiveRestartFixedIndexEnabled && type == GL_UNSIGNED_SHORT);
}
-gl::ErrorOrResult<TextureHelper11> CreateStagingTexture(GLenum textureType,
- DXGI_FORMAT dxgiFormat,
- const gl::Extents &size,
- ID3D11Device *device)
+bool IsStreamingIndexData(const gl::Context *context, GLenum srcType)
{
- if (textureType == GL_TEXTURE_2D)
+ const auto &glState = context->getGLState();
+ gl::Buffer *glBuffer = glState.getVertexArray()->getElementArrayBuffer().get();
+
+ // Case 1: the indices are passed by pointer, which forces the streaming of index data
+ if (glBuffer == nullptr)
{
- D3D11_TEXTURE2D_DESC stagingDesc;
- stagingDesc.Width = size.width;
- stagingDesc.Height = size.height;
- stagingDesc.MipLevels = 1;
- stagingDesc.ArraySize = 1;
- stagingDesc.Format = dxgiFormat;
- stagingDesc.SampleDesc.Count = 1;
- stagingDesc.SampleDesc.Quality = 0;
- stagingDesc.Usage = D3D11_USAGE_STAGING;
- stagingDesc.BindFlags = 0;
- stagingDesc.CPUAccessFlags = D3D11_CPU_ACCESS_READ;
- stagingDesc.MiscFlags = 0;
+ return true;
+ }
- ID3D11Texture2D *stagingTex = nullptr;
- HRESULT result = device->CreateTexture2D(&stagingDesc, nullptr, &stagingTex);
- if (FAILED(result))
- {
- return gl::Error(GL_OUT_OF_MEMORY, "CreateStagingTextureFor failed, HRESULT: 0x%X.",
- result);
- }
+ bool primitiveRestartWorkaround =
+ UsePrimitiveRestartWorkaround(glState.isPrimitiveRestartEnabled(), srcType);
+
+ BufferD3D *buffer = GetImplAs<BufferD3D>(glBuffer);
+ const GLenum dstType = (srcType == GL_UNSIGNED_INT || primitiveRestartWorkaround)
+ ? GL_UNSIGNED_INT
+ : GL_UNSIGNED_SHORT;
- return TextureHelper11::MakeAndPossess2D(stagingTex);
+ // Case 2a: the buffer can be used directly
+ if (buffer->supportsDirectBinding() && dstType == srcType)
+ {
+ return false;
}
- ASSERT(textureType == GL_TEXTURE_3D);
- D3D11_TEXTURE3D_DESC stagingDesc;
- stagingDesc.Width = size.width;
- stagingDesc.Height = size.height;
- stagingDesc.Depth = 1;
- stagingDesc.MipLevels = 1;
- stagingDesc.Format = dxgiFormat;
- stagingDesc.Usage = D3D11_USAGE_STAGING;
- stagingDesc.BindFlags = 0;
- stagingDesc.CPUAccessFlags = D3D11_CPU_ACCESS_READ;
- stagingDesc.MiscFlags = 0;
+ // Case 2b: use a static translated copy or fall back to streaming
+ StaticIndexBufferInterface *staticBuffer = buffer->getStaticIndexBuffer();
+ if (staticBuffer == nullptr)
+ {
+ return true;
+ }
- ID3D11Texture3D *stagingTex = nullptr;
- HRESULT result = device->CreateTexture3D(&stagingDesc, nullptr, &stagingTex);
- if (FAILED(result))
+ if ((staticBuffer->getBufferSize() == 0) || (staticBuffer->getIndexType() != dstType))
{
- return gl::Error(GL_OUT_OF_MEMORY, "CreateStagingTextureFor failed, HRESULT: 0x%X.",
- result);
+ return true;
}
- return TextureHelper11::MakeAndPossess3D(stagingTex);
+ return false;
}
-bool UsePresentPathFast(const Renderer11 *renderer,
- const gl::FramebufferAttachment *framebufferAttachment)
+IndexStorageType ClassifyIndexStorage(const gl::State &glState,
+ const gl::Buffer *elementArrayBuffer,
+ GLenum elementType,
+ GLenum destElementType,
+ unsigned int offset,
+ bool *needsTranslation)
{
- if (framebufferAttachment == nullptr)
+ // No buffer bound means we are streaming from a client pointer.
+ if (!elementArrayBuffer || !IsOffsetAligned(elementType, offset))
{
- return false;
+ *needsTranslation = true;
+ return IndexStorageType::Dynamic;
}
- return (framebufferAttachment->type() == GL_FRAMEBUFFER_DEFAULT &&
- renderer->presentPathFastEnabled());
+ // The buffer can be used directly if the storage supports it and no translation needed.
+ BufferD3D *bufferD3D = GetImplAs<BufferD3D>(elementArrayBuffer);
+ if (bufferD3D->supportsDirectBinding() && destElementType == elementType)
+ {
+ *needsTranslation = false;
+ return IndexStorageType::Direct;
+ }
+
+ // Use a static copy when available.
+ StaticIndexBufferInterface *staticBuffer = bufferD3D->getStaticIndexBuffer();
+ if (staticBuffer != nullptr)
+ {
+ // Need to re-translate the static data if has never been used, or changed type.
+ *needsTranslation =
+ (staticBuffer->getBufferSize() == 0 || staticBuffer->getIndexType() != destElementType);
+ return IndexStorageType::Static;
+ }
+
+ // Static buffer not available, fall back to streaming.
+ *needsTranslation = true;
+ return IndexStorageType::Dynamic;
}
} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/renderer11_utils.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/renderer11_utils.h
index 4925a2d227..3af51bb0f6 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/renderer11_utils.h
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/renderer11_utils.h
@@ -11,12 +11,16 @@
#define LIBANGLE_RENDERER_D3D_D3D11_RENDERER11_UTILS_H_
#include <array>
+#include <functional>
#include <vector>
-#include "libANGLE/angletypes.h"
+#include "common/Color.h"
+
#include "libANGLE/Caps.h"
#include "libANGLE/Error.h"
#include "libANGLE/renderer/d3d/RendererD3D.h"
+#include "libANGLE/renderer/d3d/d3d11/ResourceManager11.h"
+#include "libANGLE/renderer/d3d/d3d11/texture_format_table.h"
namespace gl
{
@@ -27,10 +31,10 @@ namespace rx
{
class Renderer11;
class RenderTarget11;
-struct WorkaroundsD3D;
struct Renderer11DeviceCaps;
-using RenderTargetArray = std::array<ID3D11RenderTargetView *, gl::IMPLEMENTATION_MAX_DRAW_BUFFERS>;
+using RenderTargetArray = std::array<RenderTarget11 *, gl::IMPLEMENTATION_MAX_DRAW_BUFFERS>;
+using RTVArray = std::array<ID3D11RenderTargetView *, gl::IMPLEMENTATION_MAX_DRAW_BUFFERS>;
namespace gl_d3d11
{
@@ -39,7 +43,7 @@ D3D11_BLEND ConvertBlendFunc(GLenum glBlend, bool isAlpha);
D3D11_BLEND_OP ConvertBlendOp(GLenum glBlendOp);
UINT8 ConvertColorMask(bool maskRed, bool maskGreen, bool maskBlue, bool maskAlpha);
-D3D11_CULL_MODE ConvertCullMode(bool cullEnabled, GLenum cullMode);
+D3D11_CULL_MODE ConvertCullMode(bool cullEnabled, gl::CullFaceMode cullMode);
D3D11_COMPARISON_FUNC ConvertComparison(GLenum comparison);
D3D11_DEPTH_WRITE_MASK ConvertDepthMask(bool depthWriteEnabled);
@@ -48,9 +52,12 @@ D3D11_STENCIL_OP ConvertStencilOp(GLenum stencilOp);
D3D11_FILTER ConvertFilter(GLenum minFilter, GLenum magFilter, float maxAnisotropy, GLenum comparisonMode);
D3D11_TEXTURE_ADDRESS_MODE ConvertTextureWrap(GLenum wrap);
+UINT ConvertMaxAnisotropy(float maxAnisotropy, D3D_FEATURE_LEVEL featureLevel);
D3D11_QUERY ConvertQueryType(GLenum queryType);
+UINT8 GetColorMask(const gl::InternalFormat &formatInfo);
+
} // namespace gl_d3d11
namespace d3d11_gl
@@ -60,10 +67,12 @@ unsigned int GetReservedVertexUniformVectors(D3D_FEATURE_LEVEL featureLevel);
unsigned int GetReservedFragmentUniformVectors(D3D_FEATURE_LEVEL featureLevel);
-GLint GetMaximumClientVersion(D3D_FEATURE_LEVEL featureLevel);
+gl::Version GetMaximumClientVersion(D3D_FEATURE_LEVEL featureLevel);
void GenerateCaps(ID3D11Device *device, ID3D11DeviceContext *deviceContext, const Renderer11DeviceCaps &renderer11DeviceCaps, gl::Caps *caps,
gl::TextureCapsMap *textureCapsMap, gl::Extensions *extensions, gl::Limitations *limitations);
+void GetSamplePosition(GLsizei sampleCount, size_t index, GLfloat *xy);
+
} // namespace d3d11_gl
namespace d3d11
@@ -108,32 +117,45 @@ struct PositionLayerTexCoord3DVertex
void SetPositionLayerTexCoord3DVertex(PositionLayerTexCoord3DVertex* vertex, float x, float y,
unsigned int layer, float u, float v, float s);
-template <typename T>
-struct PositionDepthColorVertex
+struct PositionVertex
{
- float x, y, z;
- T r, g, b, a;
+ float x, y, z, w;
};
-template <typename T>
-void SetPositionDepthColorVertex(PositionDepthColorVertex<T>* vertex, float x, float y, float z,
- const gl::Color<T> &color)
+struct BlendStateKey final
{
- vertex->x = x;
- vertex->y = y;
- vertex->z = z;
- vertex->r = color.red;
- vertex->g = color.green;
- vertex->b = color.blue;
- vertex->a = color.alpha;
-}
+ // This will zero-initialize the struct, including padding.
+ BlendStateKey();
+
+ gl::BlendState blendState;
+
+ // An int so struct size rounds nicely.
+ uint32_t rtvMax;
+
+ uint8_t rtvMasks[D3D11_SIMULTANEOUS_RENDER_TARGET_COUNT];
+};
+
+bool operator==(const BlendStateKey &a, const BlendStateKey &b);
+bool operator!=(const BlendStateKey &a, const BlendStateKey &b);
+
+struct RasterizerStateKey final
+{
+ // This will zero-initialize the struct, including padding.
+ RasterizerStateKey();
+
+ gl::RasterizerState rasterizerState;
-HRESULT SetDebugName(ID3D11DeviceChild *resource, const char *name);
+ // Use a 32-bit int to round the struct nicely.
+ uint32_t scissorEnabled;
+};
+
+bool operator==(const RasterizerStateKey &a, const RasterizerStateKey &b);
+bool operator!=(const RasterizerStateKey &a, const RasterizerStateKey &b);
template <typename outType>
outType* DynamicCastComObject(IUnknown* object)
{
- outType *outObject = NULL;
+ outType *outObject = nullptr;
HRESULT result = object->QueryInterface(__uuidof(outType), reinterpret_cast<void**>(&outObject));
if (SUCCEEDED(result))
{
@@ -142,7 +164,7 @@ outType* DynamicCastComObject(IUnknown* object)
else
{
SafeRelease(outObject);
- return NULL;
+ return nullptr;
}
}
@@ -161,143 +183,63 @@ inline bool isDeviceLostError(HRESULT errorCode)
}
}
-inline ID3D11VertexShader *CompileVS(ID3D11Device *device, const BYTE *byteCode, size_t N, const char *name)
-{
- ID3D11VertexShader *vs = nullptr;
- HRESULT result = device->CreateVertexShader(byteCode, N, nullptr, &vs);
- ASSERT(SUCCEEDED(result));
- if (SUCCEEDED(result))
- {
- SetDebugName(vs, name);
- return vs;
- }
- return nullptr;
-}
-
-template <unsigned int N>
-ID3D11VertexShader *CompileVS(ID3D11Device *device, const BYTE (&byteCode)[N], const char *name)
-{
- return CompileVS(device, byteCode, N, name);
-}
-
-inline ID3D11GeometryShader *CompileGS(ID3D11Device *device, const BYTE *byteCode, size_t N, const char *name)
-{
- ID3D11GeometryShader *gs = nullptr;
- HRESULT result = device->CreateGeometryShader(byteCode, N, nullptr, &gs);
- ASSERT(SUCCEEDED(result));
- if (SUCCEEDED(result))
- {
- SetDebugName(gs, name);
- return gs;
- }
- return nullptr;
-}
-
-template <unsigned int N>
-ID3D11GeometryShader *CompileGS(ID3D11Device *device, const BYTE (&byteCode)[N], const char *name)
+template <ResourceType ResourceT>
+class LazyResource : angle::NonCopyable
{
- return CompileGS(device, byteCode, N, name);
-}
+ public:
+ constexpr LazyResource() : mResource() {}
+ virtual ~LazyResource() {}
-inline ID3D11PixelShader *CompilePS(ID3D11Device *device, const BYTE *byteCode, size_t N, const char *name)
-{
- ID3D11PixelShader *ps = nullptr;
- HRESULT result = device->CreatePixelShader(byteCode, N, nullptr, &ps);
- ASSERT(SUCCEEDED(result));
- if (SUCCEEDED(result))
+ virtual gl::Error resolve(Renderer11 *renderer) = 0;
+ void reset() { mResource.reset(); }
+ GetD3D11Type<ResourceT> *get() const
{
- SetDebugName(ps, name);
- return ps;
+ ASSERT(mResource.valid());
+ return mResource.get();
}
- return nullptr;
-}
-
-template <unsigned int N>
-ID3D11PixelShader *CompilePS(ID3D11Device *device, const BYTE (&byteCode)[N], const char *name)
-{
- return CompilePS(device, byteCode, N, name);
-}
-
-template <typename ResourceType>
-class LazyResource : public angle::NonCopyable
-{
- public:
- LazyResource() : mResource(nullptr), mAssociatedDevice(nullptr) {}
- virtual ~LazyResource() { release(); }
- virtual ResourceType *resolve(ID3D11Device *device) = 0;
- void release() { SafeRelease(mResource); }
+ const Resource11<GetD3D11Type<ResourceT>> &getObj() const { return mResource; }
protected:
- void checkAssociatedDevice(ID3D11Device *device);
+ LazyResource(LazyResource &&other) : mResource(std::move(other.mResource)) {}
- ResourceType *mResource;
- ID3D11Device *mAssociatedDevice;
-};
+ // Specialized in the cpp file to avoid MSVS/Clang specific code.
+ gl::Error resolveImpl(Renderer11 *renderer,
+ const GetDescType<ResourceT> &desc,
+ GetInitDataType<ResourceT> *initData,
+ const char *name);
-template <typename ResourceType>
-void LazyResource<ResourceType>::checkAssociatedDevice(ID3D11Device *device)
-{
- ASSERT(mAssociatedDevice == nullptr || device == mAssociatedDevice);
- mAssociatedDevice = device;
-}
+ Resource11<GetD3D11Type<ResourceT>> mResource;
+};
template <typename D3D11ShaderType>
-class LazyShader final : public LazyResource<D3D11ShaderType>
+class LazyShader final : public LazyResource<GetResourceTypeFromD3D11<D3D11ShaderType>()>
{
public:
// All parameters must be constexpr. Not supported in VS2013.
- LazyShader(const BYTE *byteCode,
- size_t byteCodeSize,
- const char *name)
- : mByteCode(byteCode),
- mByteCodeSize(byteCodeSize),
- mName(name)
+ constexpr LazyShader(const BYTE *byteCode, size_t byteCodeSize, const char *name)
+ : mByteCode(byteCode, byteCodeSize), mName(name)
{
}
- D3D11ShaderType *resolve(ID3D11Device *device) override;
-
- private:
- const BYTE *mByteCode;
- size_t mByteCodeSize;
- const char *mName;
-};
-
-template <>
-inline ID3D11VertexShader *LazyShader<ID3D11VertexShader>::resolve(ID3D11Device *device)
-{
- checkAssociatedDevice(device);
- if (mResource == nullptr)
+ constexpr LazyShader(LazyShader &&shader)
+ : LazyResource<GetResourceTypeFromD3D11<D3D11ShaderType>()>(std::move(shader)),
+ mByteCode(std::move(shader.mByteCode)),
+ mName(shader.mName)
{
- mResource = CompileVS(device, mByteCode, mByteCodeSize, mName);
}
- return mResource;
-}
-template <>
-inline ID3D11GeometryShader *LazyShader<ID3D11GeometryShader>::resolve(ID3D11Device *device)
-{
- checkAssociatedDevice(device);
- if (mResource == nullptr)
+ gl::Error resolve(Renderer11 *renderer) override
{
- mResource = CompileGS(device, mByteCode, mByteCodeSize, mName);
+ return this->resolveImpl(renderer, mByteCode, nullptr, mName);
}
- return mResource;
-}
-template <>
-inline ID3D11PixelShader *LazyShader<ID3D11PixelShader>::resolve(ID3D11Device *device)
-{
- checkAssociatedDevice(device);
- if (mResource == nullptr)
- {
- mResource = CompilePS(device, mByteCode, mByteCodeSize, mName);
- }
- return mResource;
-}
+ private:
+ ShaderData mByteCode;
+ const char *mName;
+};
-class LazyInputLayout final : public LazyResource<ID3D11InputLayout>
+class LazyInputLayout final : public LazyResource<ResourceType::InputLayout>
{
public:
LazyInputLayout(const D3D11_INPUT_ELEMENT_DESC *inputDesc,
@@ -305,22 +247,22 @@ class LazyInputLayout final : public LazyResource<ID3D11InputLayout>
const BYTE *byteCode,
size_t byteCodeLen,
const char *debugName);
+ ~LazyInputLayout() override;
- ID3D11InputLayout *resolve(ID3D11Device *device) override;
+ gl::Error resolve(Renderer11 *renderer) override;
private:
- std::vector<D3D11_INPUT_ELEMENT_DESC> mInputDesc;
- size_t mByteCodeLen;
- const BYTE *mByteCode;
+ InputElementArray mInputDesc;
+ ShaderData mByteCode;
const char *mDebugName;
};
-class LazyBlendState final : public LazyResource<ID3D11BlendState>
+class LazyBlendState final : public LazyResource<ResourceType::BlendState>
{
public:
LazyBlendState(const D3D11_BLEND_DESC &desc, const char *debugName);
- ID3D11BlendState *resolve(ID3D11Device *device) override;
+ gl::Error resolve(Renderer11 *renderer) override;
private:
D3D11_BLEND_DESC mDesc;
@@ -342,48 +284,147 @@ void SetBufferData(ID3D11DeviceContext *context, ID3D11Buffer *constantBuffer, c
}
}
-WorkaroundsD3D GenerateWorkarounds(D3D_FEATURE_LEVEL featureLevel);
+angle::WorkaroundsD3D GenerateWorkarounds(const Renderer11DeviceCaps &deviceCaps,
+ const DXGI_ADAPTER_DESC &adapterDesc);
+
+enum ReservedConstantBufferSlot
+{
+ RESERVED_CONSTANT_BUFFER_SLOT_DEFAULT_UNIFORM_BLOCK = 0,
+ RESERVED_CONSTANT_BUFFER_SLOT_DRIVER = 1,
+
+ RESERVED_CONSTANT_BUFFER_SLOT_COUNT = 2
+};
+
+void InitConstantBufferDesc(D3D11_BUFFER_DESC *constantBufferDescription, size_t byteWidth);
} // namespace d3d11
+struct GenericData
+{
+ GenericData() {}
+ ~GenericData()
+ {
+ if (object)
+ {
+ // We can have a nullptr factory when holding passed-in resources.
+ if (manager)
+ {
+ manager->onReleaseGeneric(resourceType, object);
+ manager = nullptr;
+ }
+ object->Release();
+ object = nullptr;
+ }
+ }
+
+ ResourceType resourceType = ResourceType::Last;
+ ID3D11Resource *object = nullptr;
+ ResourceManager11 *manager = nullptr;
+};
+
// A helper class which wraps a 2D or 3D texture.
-class TextureHelper11 : angle::NonCopyable
+class TextureHelper11 : public Resource11Base<ID3D11Resource, std::shared_ptr, GenericData>
{
public:
TextureHelper11();
- TextureHelper11(TextureHelper11 &&toCopy);
- ~TextureHelper11();
- TextureHelper11 &operator=(TextureHelper11 &&texture);
-
- static TextureHelper11 MakeAndReference(ID3D11Resource *genericResource);
- static TextureHelper11 MakeAndPossess2D(ID3D11Texture2D *texToOwn);
- static TextureHelper11 MakeAndPossess3D(ID3D11Texture3D *texToOwn);
-
- GLenum getTextureType() const { return mTextureType; }
+ TextureHelper11(TextureHelper11 &&other);
+ TextureHelper11(const TextureHelper11 &other);
+ ~TextureHelper11() override;
+ TextureHelper11 &operator=(TextureHelper11 &&other);
+ TextureHelper11 &operator=(const TextureHelper11 &other);
+
+ bool is2D() const { return mData->resourceType == ResourceType::Texture2D; }
+ bool is3D() const { return mData->resourceType == ResourceType::Texture3D; }
+ ResourceType getTextureType() const { return mData->resourceType; }
gl::Extents getExtents() const { return mExtents; }
- DXGI_FORMAT getFormat() const { return mFormat; }
+ DXGI_FORMAT getFormat() const { return mFormatSet->texFormat; }
+ const d3d11::Format &getFormatSet() const { return *mFormatSet; }
int getSampleCount() const { return mSampleCount; }
- ID3D11Texture2D *getTexture2D() const { return mTexture2D; }
- ID3D11Texture3D *getTexture3D() const { return mTexture3D; }
- ID3D11Resource *getResource() const;
+
+ template <typename DescT, typename ResourceT>
+ void init(Resource11<ResourceT> &&texture, const DescT &desc, const d3d11::Format &format)
+ {
+ std::swap(mData->manager, texture.mData->manager);
+
+ // Can't use std::swap because texture is typed, and here we use ID3D11Resource.
+ ID3D11Resource *temp = mData->object;
+ mData->object = texture.mData->object;
+ texture.mData->object = static_cast<ResourceT *>(temp);
+
+ mFormatSet = &format;
+ initDesc(desc);
+ }
+
+ template <typename ResourceT>
+ void set(ResourceT *object, const d3d11::Format &format)
+ {
+ ASSERT(!valid());
+ mFormatSet = &format;
+ mData->object = object;
+ mData->manager = nullptr;
+
+ GetDescFromD3D11<ResourceT> desc;
+ getDesc(&desc);
+ initDesc(desc);
+ }
+
+ bool operator==(const TextureHelper11 &other) const;
+ bool operator!=(const TextureHelper11 &other) const;
+
+ void getDesc(D3D11_TEXTURE2D_DESC *desc) const;
+ void getDesc(D3D11_TEXTURE3D_DESC *desc) const;
private:
- void reset();
- void initDesc();
+ void initDesc(const D3D11_TEXTURE2D_DESC &desc2D);
+ void initDesc(const D3D11_TEXTURE3D_DESC &desc3D);
- GLenum mTextureType;
+ const d3d11::Format *mFormatSet;
gl::Extents mExtents;
- DXGI_FORMAT mFormat;
int mSampleCount;
- ID3D11Texture2D *mTexture2D;
- ID3D11Texture3D *mTexture3D;
};
-gl::ErrorOrResult<TextureHelper11> CreateStagingTexture(GLenum textureType,
- DXGI_FORMAT dxgiFormat,
- const gl::Extents &size,
- ID3D11Device *device);
+enum class StagingAccess
+{
+ READ,
+ READ_WRITE,
+};
bool UsePresentPathFast(const Renderer11 *renderer, const gl::FramebufferAttachment *colorbuffer);
+bool UsePrimitiveRestartWorkaround(bool primitiveRestartFixedIndexEnabled, GLenum type);
+bool IsStreamingIndexData(const gl::Context *context, GLenum srcType);
+
+enum class IndexStorageType
+{
+ // Dynamic indexes are re-streamed every frame. They come from a client data pointer or
+ // from buffers that are updated frequently.
+ Dynamic,
+
+ // Static indexes are translated from the original storage once, and re-used multiple times.
+ Static,
+
+ // Direct indexes are never transated and are used directly from the source buffer. They are
+ // the fastest available path.
+ Direct,
+
+ // Not a real storage type.
+ Invalid,
+};
+
+IndexStorageType ClassifyIndexStorage(const gl::State &glState,
+ const gl::Buffer *elementArrayBuffer,
+ GLenum elementType,
+ GLenum destElementType,
+ unsigned int offset,
+ bool *needsTranslation);
+
+// Used for state change notifications between buffers and vertex arrays.
+using OnBufferDataDirtyBinding = angle::ChannelBinding<size_t, const gl::Context *>;
+using OnBufferDataDirtyChannel = angle::BroadcastChannel<size_t, const gl::Context *>;
+using OnBufferDataDirtyReceiver = angle::SignalReceiver<size_t, const gl::Context *>;
+
+// Used for state change notifications between RenderTarget11 and Framebuffer11.
+using OnRenderTargetDirtyBinding = angle::ChannelBinding<size_t, const gl::Context *>;
+using OnRenderTargetDirtyChannel = angle::BroadcastChannel<size_t, const gl::Context *>;
+using OnRenderTargetDirtyReceiver = angle::SignalReceiver<size_t, const gl::Context *>;
} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/shaders/Clear11.hlsl b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/shaders/Clear11.hlsl
index 2b3e1ebe4c..48f5b427ec 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/shaders/Clear11.hlsl
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/shaders/Clear11.hlsl
@@ -1,13 +1,152 @@
-// Assume we are in SM4+, which has 8 color outputs
+//
+// Copyright (c) 2017 The ANGLE Project. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+//
-void VS_ClearFloat( in float3 inPosition : POSITION, in float4 inColor : COLOR,
- out float4 outPosition : SV_POSITION, out float4 outColor : COLOR)
+// Clear11.hlsl: Shaders for clearing RTVs and DSVs using draw calls and
+// specifying float depth values and either float, uint or sint clear colors.
+// Notes:
+// - UINT & SINT clears can only be compiled with FL10+
+// - VS_Clear_FL9 requires a VB to be bound with vertices to create
+// a primitive covering the entire surface (in clip co-ordinates)
+
+// Constants
+static const float2 g_Corners[6] =
+{
+ float2(-1.0f, 1.0f),
+ float2( 1.0f, -1.0f),
+ float2(-1.0f, -1.0f),
+ float2(-1.0f, 1.0f),
+ float2( 1.0f, 1.0f),
+ float2( 1.0f, -1.0f),
+};
+
+// Vertex Shaders
+void VS_Clear(in uint id : SV_VertexID,
+ out float4 outPosition : SV_POSITION)
+{
+ float2 corner = g_Corners[id];
+ outPosition = float4(corner.x, corner.y, 0.0f, 1.0f);
+}
+
+void VS_Multiview_Clear(in uint id : SV_VertexID,
+ in uint instanceID : SV_InstanceID,
+ out float4 outPosition : SV_POSITION,
+ out uint outLayerID : TEXCOORD0)
+{
+ float2 corner = g_Corners[id];
+ outPosition = float4(corner.x, corner.y, 0.0f, 1.0f);
+ outLayerID = instanceID;
+}
+
+void VS_Clear_FL9( in float4 inPosition : POSITION,
+ out float4 outPosition : SV_POSITION)
+{
+ outPosition = inPosition;
+}
+
+// Geometry shader for clearing multiview layered textures
+struct GS_INPUT
+{
+ float4 inPosition : SV_Position;
+ uint inLayerID : TEXCOORD0;
+};
+
+struct GS_OUTPUT
{
- outPosition = float4(inPosition, 1.0f);
- outColor = inColor;
+ float4 outPosition : SV_Position;
+ uint outLayerID : SV_RenderTargetArrayIndex;
+};
+
+[maxvertexcount(3)]
+void GS_Multiview_Clear(triangle GS_INPUT input[3], inout TriangleStream<GS_OUTPUT> outStream)
+{
+ GS_OUTPUT output = (GS_OUTPUT)0;
+ for (int i = 0; i < 3; i++)
+ {
+ output.outPosition = input[i].inPosition;
+ output.outLayerID = input[i].inLayerID;
+ outStream.Append(output);
+ }
+ outStream.RestartStrip();
+}
+
+// Pixel Shader Constant Buffers
+cbuffer ColorAndDepthDataFloat : register(b0)
+{
+ float4 color_Float : packoffset(c0);
+ float zValueF_Float : packoffset(c1);
+}
+
+cbuffer ColorAndDepthDataSint : register(b0)
+{
+ int4 color_Sint : packoffset(c0);
+ float zValueF_Sint : packoffset(c1);
+}
+
+cbuffer ColorAndDepthDataUint : register(b0)
+{
+ uint4 color_Uint : packoffset(c0);
+ float zValueF_Uint : packoffset(c1);
}
-struct PS_OutputFloat
+cbuffer DepthOnlyData : register(b0)
+{
+ float zValue_Depth : packoffset(c1);
+}
+
+// Pixel Shader Output Structs
+struct PS_OutputFloat_FL9
+{
+ float4 color0 : SV_TARGET0;
+ float4 color1 : SV_TARGET1;
+ float4 color2 : SV_TARGET2;
+ float4 color3 : SV_TARGET3;
+ float depth : SV_DEPTH;
+};
+
+struct PS_OutputFloat1
+{
+ float4 color0 : SV_TARGET0;
+ float depth : SV_DEPTH;
+};
+
+struct PS_OutputFloat2
+{
+ float4 color0 : SV_TARGET0;
+ float4 color1 : SV_TARGET1;
+ float depth : SV_DEPTH;
+};
+
+struct PS_OutputFloat3
+{
+ float4 color0 : SV_TARGET0;
+ float4 color1 : SV_TARGET1;
+ float4 color2 : SV_TARGET2;
+ float depth : SV_DEPTH;
+};
+
+struct PS_OutputFloat4
+{
+ float4 color0 : SV_TARGET0;
+ float4 color1 : SV_TARGET1;
+ float4 color2 : SV_TARGET2;
+ float4 color3 : SV_TARGET3;
+ float depth : SV_DEPTH;
+};
+
+struct PS_OutputFloat5
+{
+ float4 color0 : SV_TARGET0;
+ float4 color1 : SV_TARGET1;
+ float4 color2 : SV_TARGET2;
+ float4 color3 : SV_TARGET3;
+ float4 color4 : SV_TARGET4;
+ float depth : SV_DEPTH;
+};
+
+struct PS_OutputFloat6
{
float4 color0 : SV_TARGET0;
float4 color1 : SV_TARGET1;
@@ -15,50 +154,98 @@ struct PS_OutputFloat
float4 color3 : SV_TARGET3;
float4 color4 : SV_TARGET4;
float4 color5 : SV_TARGET5;
- float4 color6 : SV_TARGET6;
- float4 color7 : SV_TARGET7;
+ float depth : SV_DEPTH;
};
-PS_OutputFloat PS_ClearFloat(in float4 inPosition : SV_POSITION, in float4 inColor : COLOR)
+struct PS_OutputFloat7
{
- PS_OutputFloat outColor;
- outColor.color0 = inColor;
- outColor.color1 = inColor;
- outColor.color2 = inColor;
- outColor.color3 = inColor;
- outColor.color4 = inColor;
- outColor.color5 = inColor;
- outColor.color6 = inColor;
- outColor.color7 = inColor;
- return outColor;
-}
+ float4 color0 : SV_TARGET0;
+ float4 color1 : SV_TARGET1;
+ float4 color2 : SV_TARGET2;
+ float4 color3 : SV_TARGET3;
+ float4 color4 : SV_TARGET4;
+ float4 color5 : SV_TARGET5;
+ float4 color6 : SV_TARGET6;
+ float depth : SV_DEPTH;
+};
-struct PS_OutputFloat_FL9
+struct PS_OutputFloat8
{
float4 color0 : SV_TARGET0;
float4 color1 : SV_TARGET1;
float4 color2 : SV_TARGET2;
float4 color3 : SV_TARGET3;
+ float4 color4 : SV_TARGET4;
+ float4 color5 : SV_TARGET5;
+ float4 color6 : SV_TARGET6;
+ float4 color7 : SV_TARGET7;
+ float depth : SV_DEPTH;
};
-PS_OutputFloat_FL9 PS_ClearFloat_FL9(in float4 inPosition : SV_POSITION, in float4 inColor : COLOR)
+struct PS_OutputUint1
{
- PS_OutputFloat_FL9 outColor;
- outColor.color0 = inColor;
- outColor.color1 = inColor;
- outColor.color2 = inColor;
- outColor.color3 = inColor;
- return outColor;
-}
+ uint4 color0 : SV_TARGET0;
+ float depth : SV_DEPTH;
+};
-void VS_ClearUint( in float3 inPosition : POSITION, in uint4 inColor : COLOR,
- out float4 outPosition : SV_POSITION, out uint4 outColor : COLOR)
+struct PS_OutputUint2
{
- outPosition = float4(inPosition, 1.0f);
- outColor = inColor;
-}
+ uint4 color0 : SV_TARGET0;
+ uint4 color1 : SV_TARGET1;
+ float depth : SV_DEPTH;
+};
+
+struct PS_OutputUint3
+{
+ uint4 color0 : SV_TARGET0;
+ uint4 color1 : SV_TARGET1;
+ uint4 color2 : SV_TARGET2;
+ float depth : SV_DEPTH;
+};
+
+struct PS_OutputUint4
+{
+ uint4 color0 : SV_TARGET0;
+ uint4 color1 : SV_TARGET1;
+ uint4 color2 : SV_TARGET2;
+ uint4 color3 : SV_TARGET3;
+ float depth : SV_DEPTH;
+};
+
+struct PS_OutputUint5
+{
+ uint4 color0 : SV_TARGET0;
+ uint4 color1 : SV_TARGET1;
+ uint4 color2 : SV_TARGET2;
+ uint4 color3 : SV_TARGET3;
+ uint4 color4 : SV_TARGET4;
+ float depth : SV_DEPTH;
+};
+
+struct PS_OutputUint6
+{
+ uint4 color0 : SV_TARGET0;
+ uint4 color1 : SV_TARGET1;
+ uint4 color2 : SV_TARGET2;
+ uint4 color3 : SV_TARGET3;
+ uint4 color4 : SV_TARGET4;
+ uint4 color5 : SV_TARGET5;
+ float depth : SV_DEPTH;
+};
+
+struct PS_OutputUint7
+{
+ uint4 color0 : SV_TARGET0;
+ uint4 color1 : SV_TARGET1;
+ uint4 color2 : SV_TARGET2;
+ uint4 color3 : SV_TARGET3;
+ uint4 color4 : SV_TARGET4;
+ uint4 color5 : SV_TARGET5;
+ uint4 color6 : SV_TARGET6;
+ float depth : SV_DEPTH;
+};
-struct PS_OutputUint
+struct PS_OutputUint8
{
uint4 color0 : SV_TARGET0;
uint4 color1 : SV_TARGET1;
@@ -68,31 +255,73 @@ struct PS_OutputUint
uint4 color5 : SV_TARGET5;
uint4 color6 : SV_TARGET6;
uint4 color7 : SV_TARGET7;
+ float depth : SV_DEPTH;
};
-PS_OutputUint PS_ClearUint(in float4 inPosition : SV_POSITION, in uint4 inColor : COLOR)
+struct PS_OutputSint1
{
- PS_OutputUint outColor;
- outColor.color0 = inColor;
- outColor.color1 = inColor;
- outColor.color2 = inColor;
- outColor.color3 = inColor;
- outColor.color4 = inColor;
- outColor.color5 = inColor;
- outColor.color6 = inColor;
- outColor.color7 = inColor;
- return outColor;
-}
+ int4 color0 : SV_TARGET0;
+ float depth : SV_DEPTH;
+};
+struct PS_OutputSint2
+{
+ int4 color0 : SV_TARGET0;
+ int4 color1 : SV_TARGET1;
+ float depth : SV_DEPTH;
+};
-void VS_ClearSint( in float3 inPosition : POSITION, in int4 inColor : COLOR,
- out float4 outPosition : SV_POSITION, out int4 outColor : COLOR)
+struct PS_OutputSint3
{
- outPosition = float4(inPosition, 1.0f);
- outColor = inColor;
-}
+ int4 color0 : SV_TARGET0;
+ int4 color1 : SV_TARGET1;
+ int4 color2 : SV_TARGET2;
+ float depth : SV_DEPTH;
+};
+
+struct PS_OutputSint4
+{
+ int4 color0 : SV_TARGET0;
+ int4 color1 : SV_TARGET1;
+ int4 color2 : SV_TARGET2;
+ int4 color3 : SV_TARGET3;
+ float depth : SV_DEPTH;
+};
+
+struct PS_OutputSint5
+{
+ int4 color0 : SV_TARGET0;
+ int4 color1 : SV_TARGET1;
+ int4 color2 : SV_TARGET2;
+ int4 color3 : SV_TARGET3;
+ int4 color4 : SV_TARGET4;
+ float depth : SV_DEPTH;
+};
+
+struct PS_OutputSint6
+{
+ int4 color0 : SV_TARGET0;
+ int4 color1 : SV_TARGET1;
+ int4 color2 : SV_TARGET2;
+ int4 color3 : SV_TARGET3;
+ int4 color4 : SV_TARGET4;
+ int4 color5 : SV_TARGET5;
+ float depth : SV_DEPTH;
+};
+
+struct PS_OutputSint7
+{
+ int4 color0 : SV_TARGET0;
+ int4 color1 : SV_TARGET1;
+ int4 color2 : SV_TARGET2;
+ int4 color3 : SV_TARGET3;
+ int4 color4 : SV_TARGET4;
+ int4 color5 : SV_TARGET5;
+ int4 color6 : SV_TARGET6;
+ float depth : SV_DEPTH;
+};
-struct PS_OutputSint
+struct PS_OutputSint8
{
int4 color0 : SV_TARGET0;
int4 color1 : SV_TARGET1;
@@ -102,18 +331,305 @@ struct PS_OutputSint
int4 color5 : SV_TARGET5;
int4 color6 : SV_TARGET6;
int4 color7 : SV_TARGET7;
+ float depth : SV_DEPTH;
+};
+
+struct PS_OutputDepth
+{
+ float depth : SV_DEPTH;
};
-PS_OutputSint PS_ClearSint(in float4 inPosition : SV_POSITION, in int4 inColor : COLOR)
+// Pixel Shaders
+PS_OutputFloat_FL9 PS_ClearFloat_FL9(in float4 inPosition : SV_POSITION)
+{
+ PS_OutputFloat_FL9 outData;
+ outData.color0 = color_Float;
+ outData.color1 = color_Float;
+ outData.color2 = color_Float;
+ outData.color3 = color_Float;
+ outData.depth = zValueF_Float;
+ return outData;
+}
+
+PS_OutputFloat1 PS_ClearFloat1(in float4 inPosition : SV_POSITION)
+{
+ PS_OutputFloat1 outData;
+ outData.color0 = color_Float;
+ outData.depth = zValueF_Float;
+ return outData;
+}
+
+PS_OutputFloat2 PS_ClearFloat2(in float4 inPosition : SV_POSITION)
+{
+ PS_OutputFloat2 outData;
+ outData.color0 = color_Float;
+ outData.color1 = color_Float;
+ outData.depth = zValueF_Float;
+ return outData;
+}
+
+PS_OutputFloat3 PS_ClearFloat3(in float4 inPosition : SV_POSITION)
+{
+ PS_OutputFloat3 outData;
+ outData.color0 = color_Float;
+ outData.color1 = color_Float;
+ outData.color2 = color_Float;
+ outData.depth = zValueF_Float;
+ return outData;
+}
+
+PS_OutputFloat4 PS_ClearFloat4(in float4 inPosition : SV_POSITION)
+{
+ PS_OutputFloat4 outData;
+ outData.color0 = color_Float;
+ outData.color1 = color_Float;
+ outData.color2 = color_Float;
+ outData.color3 = color_Float;
+ outData.depth = zValueF_Float;
+ return outData;
+}
+
+PS_OutputFloat5 PS_ClearFloat5(in float4 inPosition : SV_POSITION)
+{
+ PS_OutputFloat5 outData;
+ outData.color0 = color_Float;
+ outData.color1 = color_Float;
+ outData.color2 = color_Float;
+ outData.color3 = color_Float;
+ outData.color4 = color_Float;
+ outData.depth = zValueF_Float;
+ return outData;
+}
+
+PS_OutputFloat6 PS_ClearFloat6(in float4 inPosition : SV_POSITION)
+{
+ PS_OutputFloat6 outData;
+ outData.color0 = color_Float;
+ outData.color1 = color_Float;
+ outData.color2 = color_Float;
+ outData.color3 = color_Float;
+ outData.color4 = color_Float;
+ outData.color5 = color_Float;
+ outData.depth = zValueF_Float;
+ return outData;
+}
+
+PS_OutputFloat7 PS_ClearFloat7(in float4 inPosition : SV_POSITION)
+{
+ PS_OutputFloat7 outData;
+ outData.color0 = color_Float;
+ outData.color1 = color_Float;
+ outData.color2 = color_Float;
+ outData.color3 = color_Float;
+ outData.color4 = color_Float;
+ outData.color5 = color_Float;
+ outData.color6 = color_Float;
+ outData.depth = zValueF_Float;
+ return outData;
+}
+
+PS_OutputFloat8 PS_ClearFloat8(in float4 inPosition : SV_POSITION)
+{
+ PS_OutputFloat8 outData;
+ outData.color0 = color_Float;
+ outData.color1 = color_Float;
+ outData.color2 = color_Float;
+ outData.color3 = color_Float;
+ outData.color4 = color_Float;
+ outData.color5 = color_Float;
+ outData.color6 = color_Float;
+ outData.color7 = color_Float;
+ outData.depth = zValueF_Float;
+ return outData;
+}
+
+PS_OutputUint1 PS_ClearUint1(in float4 inPosition : SV_POSITION)
+{
+ PS_OutputUint1 outData;
+ outData.color0 = color_Uint;
+ outData.depth = zValueF_Uint;
+ return outData;
+}
+
+PS_OutputUint2 PS_ClearUint2(in float4 inPosition : SV_POSITION)
+{
+ PS_OutputUint2 outData;
+ outData.color0 = color_Uint;
+ outData.color1 = color_Uint;
+ outData.depth = zValueF_Uint;
+ return outData;
+}
+
+PS_OutputUint3 PS_ClearUint3(in float4 inPosition : SV_POSITION)
+{
+ PS_OutputUint3 outData;
+ outData.color0 = color_Uint;
+ outData.color1 = color_Uint;
+ outData.color2 = color_Uint;
+ outData.depth = zValueF_Uint;
+ return outData;
+}
+
+PS_OutputUint4 PS_ClearUint4(in float4 inPosition : SV_POSITION)
+{
+ PS_OutputUint4 outData;
+ outData.color0 = color_Uint;
+ outData.color1 = color_Uint;
+ outData.color2 = color_Uint;
+ outData.color3 = color_Uint;
+ outData.depth = zValueF_Uint;
+ return outData;
+}
+
+PS_OutputUint5 PS_ClearUint5(in float4 inPosition : SV_POSITION)
+{
+ PS_OutputUint5 outData;
+ outData.color0 = color_Uint;
+ outData.color1 = color_Uint;
+ outData.color2 = color_Uint;
+ outData.color3 = color_Uint;
+ outData.color4 = color_Uint;
+ outData.depth = zValueF_Uint;
+ return outData;
+}
+
+PS_OutputUint6 PS_ClearUint6(in float4 inPosition : SV_POSITION)
+{
+ PS_OutputUint6 outData;
+ outData.color0 = color_Uint;
+ outData.color1 = color_Uint;
+ outData.color2 = color_Uint;
+ outData.color3 = color_Uint;
+ outData.color4 = color_Uint;
+ outData.color5 = color_Uint;
+ outData.depth = zValueF_Uint;
+ return outData;
+}
+
+PS_OutputUint7 PS_ClearUint7(in float4 inPosition : SV_POSITION)
+{
+ PS_OutputUint7 outData;
+ outData.color0 = color_Uint;
+ outData.color1 = color_Uint;
+ outData.color2 = color_Uint;
+ outData.color3 = color_Uint;
+ outData.color4 = color_Uint;
+ outData.color5 = color_Uint;
+ outData.color6 = color_Uint;
+ outData.depth = zValueF_Uint;
+ return outData;
+}
+
+PS_OutputUint8 PS_ClearUint8(in float4 inPosition : SV_POSITION)
+{
+ PS_OutputUint8 outData;
+ outData.color0 = color_Uint;
+ outData.color1 = color_Uint;
+ outData.color2 = color_Uint;
+ outData.color3 = color_Uint;
+ outData.color4 = color_Uint;
+ outData.color5 = color_Uint;
+ outData.color6 = color_Uint;
+ outData.color7 = color_Uint;
+ outData.depth = zValueF_Uint;
+ return outData;
+}
+
+PS_OutputSint1 PS_ClearSint1(in float4 inPosition : SV_POSITION)
+{
+ PS_OutputSint1 outData;
+ outData.color0 = color_Sint;
+ outData.depth = zValueF_Sint;
+ return outData;
+}
+
+PS_OutputSint2 PS_ClearSint2(in float4 inPosition : SV_POSITION)
+{
+ PS_OutputSint2 outData;
+ outData.color0 = color_Sint;
+ outData.color1 = color_Sint;
+ outData.depth = zValueF_Sint;
+ return outData;
+}
+
+PS_OutputSint3 PS_ClearSint3(in float4 inPosition : SV_POSITION)
+{
+ PS_OutputSint3 outData;
+ outData.color0 = color_Sint;
+ outData.color1 = color_Sint;
+ outData.color2 = color_Sint;
+ outData.depth = zValueF_Sint;
+ return outData;
+}
+
+PS_OutputSint4 PS_ClearSint4(in float4 inPosition : SV_POSITION)
+{
+ PS_OutputSint4 outData;
+ outData.color0 = color_Sint;
+ outData.color1 = color_Sint;
+ outData.color2 = color_Sint;
+ outData.color3 = color_Sint;
+ outData.depth = zValueF_Sint;
+ return outData;
+}
+
+PS_OutputSint5 PS_ClearSint5(in float4 inPosition : SV_POSITION)
+{
+ PS_OutputSint5 outData;
+ outData.color0 = color_Sint;
+ outData.color1 = color_Sint;
+ outData.color2 = color_Sint;
+ outData.color3 = color_Sint;
+ outData.color4 = color_Sint;
+ outData.depth = zValueF_Sint;
+ return outData;
+}
+
+PS_OutputSint6 PS_ClearSint6(in float4 inPosition : SV_POSITION)
+{
+ PS_OutputSint6 outData;
+ outData.color0 = color_Sint;
+ outData.color1 = color_Sint;
+ outData.color2 = color_Sint;
+ outData.color3 = color_Sint;
+ outData.color4 = color_Sint;
+ outData.color5 = color_Sint;
+ outData.depth = zValueF_Sint;
+ return outData;
+}
+
+PS_OutputSint7 PS_ClearSint7(in float4 inPosition : SV_POSITION)
+{
+ PS_OutputSint7 outData;
+ outData.color0 = color_Sint;
+ outData.color1 = color_Sint;
+ outData.color2 = color_Sint;
+ outData.color3 = color_Sint;
+ outData.color4 = color_Sint;
+ outData.color5 = color_Sint;
+ outData.color6 = color_Sint;
+ outData.depth = zValueF_Sint;
+ return outData;
+}
+
+PS_OutputSint8 PS_ClearSint8(in float4 inPosition : SV_POSITION)
+{
+ PS_OutputSint8 outData;
+ outData.color0 = color_Sint;
+ outData.color1 = color_Sint;
+ outData.color2 = color_Sint;
+ outData.color3 = color_Sint;
+ outData.color4 = color_Sint;
+ outData.color5 = color_Sint;
+ outData.color6 = color_Sint;
+ outData.color7 = color_Sint;
+ outData.depth = zValueF_Sint;
+ return outData;
+}
+
+PS_OutputDepth PS_ClearDepth(in float4 inPosition : SV_POSITION)
{
- PS_OutputSint outColor;
- outColor.color0 = inColor;
- outColor.color1 = inColor;
- outColor.color2 = inColor;
- outColor.color3 = inColor;
- outColor.color4 = inColor;
- outColor.color5 = inColor;
- outColor.color6 = inColor;
- outColor.color7 = inColor;
- return outColor;
+ PS_OutputDepth outData;
+ outData.depth = zValue_Depth;
+ return outData;
}
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/shaders/MultiplyAlpha.hlsl b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/shaders/MultiplyAlpha.hlsl
new file mode 100644
index 0000000000..0d10b8eafa
--- /dev/null
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/shaders/MultiplyAlpha.hlsl
@@ -0,0 +1,131 @@
+Texture2D<float4> TextureF : register(t0);
+Texture2D<uint4> TextureUI : register(t0);
+
+SamplerState Sampler : register(s0);
+
+// Notation:
+// PM: premultiply, UM: unmulitply, PT: passthrough
+// F: float, U: uint
+
+// Float to float LUMA
+float4 PS_FtoF_PM_LUMA(in float4 inPosition : SV_POSITION, in float2 inTexCoord : TEXCOORD0) : SV_TARGET0
+{
+ float4 color = TextureF.Sample(Sampler, inTexCoord).rgba;
+ color.rgb = color.r * color.a;
+ color.a = 1.0f;
+ return color;
+}
+float4 PS_FtoF_UM_LUMA(in float4 inPosition : SV_POSITION, in float2 inTexCoord : TEXCOORD0) : SV_TARGET0
+{
+ float4 color = TextureF.Sample(Sampler, inTexCoord).rgba;
+ if (color.a > 0.0f)
+ {
+ color.rgb = color.r / color.a;
+ }
+ color.a = 1.0f;
+ return color;
+}
+
+// Float to float LUMAALPHA
+float4 PS_FtoF_PM_LUMAALPHA(in float4 inPosition : SV_POSITION, in float2 inTexCoord : TEXCOORD0) : SV_TARGET0
+{
+ float4 color = TextureF.Sample(Sampler, inTexCoord).rgba;
+ color.rgb = color.r * color.a;
+ return color;
+}
+
+float4 PS_FtoF_UM_LUMAALPHA(in float4 inPosition : SV_POSITION, in float2 inTexCoord : TEXCOORD0) : SV_TARGET0
+{
+ float4 color = TextureF.Sample(Sampler, inTexCoord).rgba;
+ if (color.a > 0.0f)
+ {
+ color.rgb = color.r / color.a;
+ }
+ return color;
+}
+
+// Float to float RGBA
+float4 PS_FtoF_PM_RGBA(in float4 inPosition : SV_POSITION, in float2 inTexCoord : TEXCOORD0) : SV_TARGET0
+{
+ float4 color = TextureF.Sample(Sampler, inTexCoord).rgba;
+ color.rgb *= color.a;
+ return color;
+}
+
+float4 PS_FtoF_UM_RGBA(in float4 inPosition : SV_POSITION, in float2 inTexCoord : TEXCOORD0) : SV_TARGET0
+{
+ float4 color = TextureF.Sample(Sampler, inTexCoord).rgba;
+ if (color.a > 0.0f)
+ {
+ color.rgb /= color.a;
+ }
+ return color;
+}
+
+// Float to float RGB
+float4 PS_FtoF_PM_RGB(in float4 inPosition : SV_POSITION, in float2 inTexCoord : TEXCOORD0) : SV_TARGET0
+{
+ float4 color = TextureF.Sample(Sampler, inTexCoord).rgba;
+ color.rgb *= color.a;
+ color.a = 1.0f;
+ return color;
+}
+
+float4 PS_FtoF_UM_RGB(in float4 inPosition : SV_POSITION, in float2 inTexCoord : TEXCOORD0) : SV_TARGET0
+{
+ float4 color = TextureF.Sample(Sampler, inTexCoord).rgba;
+ if (color.a > 0.0f)
+ {
+ color.rgb /= color.a;
+ }
+ color.a = 1.0f;
+ return color;
+}
+
+// Float to uint RGBA
+uint4 PS_FtoU_PT_RGBA(in float4 inPosition : SV_POSITION, in float2 inTexCoord : TEXCOORD0) : SV_TARGET0
+{
+ float4 color = TextureF.Sample(Sampler, inTexCoord).rgba;
+ return uint4(color * 255);
+}
+
+uint4 PS_FtoU_PM_RGBA(in float4 inPosition : SV_POSITION, in float2 inTexCoord : TEXCOORD0) : SV_TARGET0
+{
+ float4 color = TextureF.Sample(Sampler, inTexCoord).rgba;
+ color.rgb *= color.a;
+ return uint4(color * 255);
+}
+
+uint4 PS_FtoU_UM_RGBA(in float4 inPosition : SV_POSITION, in float2 inTexCoord : TEXCOORD0) : SV_TARGET0
+{
+ float4 color = TextureF.Sample(Sampler, inTexCoord).rgba;
+ if (color.a > 0.0f)
+ {
+ color.rgb /= color.a;
+ }
+ return uint4(color * 255);
+}
+
+// Float to uint RGB
+uint4 PS_FtoU_PT_RGB(in float4 inPosition : SV_POSITION, in float2 inTexCoord : TEXCOORD0) : SV_TARGET0
+{
+ float4 color = TextureF.Sample(Sampler, inTexCoord).rgba;
+ return uint4(color.rgb * 255, 1);
+}
+
+uint4 PS_FtoU_PM_RGB(in float4 inPosition : SV_POSITION, in float2 inTexCoord : TEXCOORD0) : SV_TARGET0
+{
+ float4 color = TextureF.Sample(Sampler, inTexCoord).rgba;
+ color.rgb *= color.a;
+ return uint4(color.rgb * 255, 1);
+}
+
+uint4 PS_FtoU_UM_RGB(in float4 inPosition : SV_POSITION, in float2 inTexCoord : TEXCOORD0) : SV_TARGET0
+{
+ float4 color = TextureF.Sample(Sampler, inTexCoord).rgba;
+ if (color.a > 0.0f)
+ {
+ color.rgb /= color.a;
+ }
+ return uint4(color.rgb * 255, 1);
+}
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/shaders/Passthrough2D11.hlsl b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/shaders/Passthrough2D11.hlsl
index 8671c39fb7..0b1a5ad169 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/shaders/Passthrough2D11.hlsl
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/shaders/Passthrough2D11.hlsl
@@ -1,4 +1,5 @@
Texture2D<float4> TextureF : register(t0);
+Texture2DMS<float4> TextureF_MS: register(t0);
Texture2D<uint4> TextureUI : register(t0);
Texture2D<int4> TextureI : register(t0);
@@ -21,6 +22,16 @@ float4 PS_PassthroughRGBA2D(in float4 inPosition : SV_POSITION, in float2 inTexC
return TextureF.Sample(Sampler, inTexCoord).rgba;
}
+float4 PS_PassthroughA2D(in float4 inPosition : SV_POSITION, in float2 inTexCoord : TEXCOORD0) : SV_TARGET0
+{
+ return float4(0.0f, 0.0f, 0.0f, TextureF.Sample(Sampler, inTexCoord).a);
+}
+
+float4 PS_PassthroughRGBA2DMS(in float4 inPosition : SV_POSITION, in float2 inTexCoord : TEXCORD0, in uint inSampleIndex : SV_SAMPLEINDEX) : SV_TARGET0
+{
+ return TextureF_MS.sample[inSampleIndex][inTexCoord].rgba;
+}
+
uint4 PS_PassthroughRGBA2DUI(in float4 inPosition : SV_POSITION, in float2 inTexCoord : TEXCOORD0) : SV_TARGET0
{
uint2 size;
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/shaders/ResolveDepthStencil.hlsl b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/shaders/ResolveDepthStencil.hlsl
new file mode 100644
index 0000000000..7dc40d4b6a
--- /dev/null
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/shaders/ResolveDepthStencil.hlsl
@@ -0,0 +1,56 @@
+static const float2 g_Corners[6] =
+{
+ float2(-1.0f, 1.0f),
+ float2( 1.0f, -1.0f),
+ float2(-1.0f, -1.0f),
+ float2(-1.0f, 1.0f),
+ float2( 1.0f, 1.0f),
+ float2( 1.0f, -1.0f),
+};
+
+void VS_ResolveDepthStencil(in uint id : SV_VertexID,
+ out float4 position : SV_Position,
+ out float2 texCoord : TEXCOORD0)
+{
+ float2 corner = g_Corners[id];
+ position = float4(corner.x, corner.y, 0.0f, 1.0f);
+ texCoord = float2((corner.x + 1.0f) * 0.5f, (-corner.y + 1.0f) * 0.5f);
+}
+
+Texture2DMS<float> Depth : register(t0);
+Texture2DMS<uint2> Stencil : register(t1);
+
+void PS_ResolveDepth(in float4 position : SV_Position,
+ in float2 texCoord : TEXCOORD0,
+ out float depth : SV_Depth)
+{
+ // MS samplers must use Load
+ uint width, height, samples;
+ Depth.GetDimensions(width, height, samples);
+ uint2 coord = uint2(texCoord.x * float(width), texCoord.y * float(height));
+ depth = Depth.Load(coord, 0).r;
+}
+
+void PS_ResolveDepthStencil(in float4 position : SV_Position,
+ in float2 texCoord : TEXCOORD0,
+ out float2 depthStencil : SV_Target0)
+{
+ // MS samplers must use Load
+ uint width, height, samples;
+ Depth.GetDimensions(width, height, samples);
+ uint2 coord = uint2(texCoord.x * float(width), texCoord.y * float(height));
+ depthStencil.r = Depth.Load(coord, 0).r;
+ depthStencil.g = float(Stencil.Load(coord, 0).g);
+}
+
+void PS_ResolveStencil(in float4 position : SV_Position,
+ in float2 texCoord : TEXCOORD0,
+ out float2 stencil : SV_Target0)
+{
+ // MS samplers must use Load
+ uint width, height, samples;
+ Stencil.GetDimensions(width, height, samples);
+ uint2 coord = uint2(texCoord.x * float(width), texCoord.y * float(height));
+ stencil.r = 0.0f;
+ stencil.g = float(Stencil.Load(coord, 0).g);
+}
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgba2dms11ps.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgba2dms11ps.h
new file mode 100644
index 0000000000..a5cccdc98e
--- /dev/null
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/shaders/compiled/passthroughrgba2dms11ps.h
@@ -0,0 +1,155 @@
+#if 0
+//
+// Generated by Microsoft (R) HLSL Shader Compiler 10.1
+//
+//
+// Resource Bindings:
+//
+// Name Type Format Dim HLSL Bind Count
+// ------------------------------ ---------- ------- ----------- -------------- ------
+// TextureF_MS texture float4 2dMS t0 1
+//
+//
+//
+// Input signature:
+//
+// Name Index Mask Register SysValue Format Used
+// -------------------- ----- ------ -------- -------- ------- ------
+// SV_POSITION 0 xyzw 0 POS float
+// TEXCORD 0 xy 1 NONE float xy
+// SV_SAMPLEINDEX 0 x 2 SAMPLE uint x
+//
+//
+// Output signature:
+//
+// Name Index Mask Register SysValue Format Used
+// -------------------- ----- ------ -------- -------- ------- ------
+// SV_TARGET 0 xyzw 0 TARGET float xyzw
+//
+// Pixel Shader runs at sample frequency
+//
+ps_4_1
+dcl_globalFlags refactoringAllowed
+dcl_resource_texture2dms(0) (float,float,float,float) t0
+dcl_input_ps linear v1.xy
+dcl_input_ps_sgv constant v2.x, sampleIndex
+dcl_output o0.xyzw
+dcl_temps 1
+ftou r0.xy, v1.xyxx
+mov r0.zw, l(0,0,0,0)
+ldms o0.xyzw, r0.xyzw, t0.xyzw, v2.x
+ret
+// Approximately 4 instruction slots used
+#endif
+
+const BYTE g_PS_PassthroughRGBA2DMS[] =
+{
+ 68, 88, 66, 67, 206, 115,
+ 73, 27, 160, 237, 59, 223,
+ 179, 180, 28, 146, 74, 174,
+ 29, 197, 1, 0, 0, 0,
+ 136, 2, 0, 0, 5, 0,
+ 0, 0, 52, 0, 0, 0,
+ 172, 0, 0, 0, 40, 1,
+ 0, 0, 92, 1, 0, 0,
+ 12, 2, 0, 0, 82, 68,
+ 69, 70, 112, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0,
+ 0, 0, 1, 0, 0, 0,
+ 28, 0, 0, 0, 1, 4,
+ 255, 255, 0, 1, 0, 0,
+ 72, 0, 0, 0, 60, 0,
+ 0, 0, 2, 0, 0, 0,
+ 5, 0, 0, 0, 6, 0,
+ 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 1, 0,
+ 0, 0, 13, 0, 0, 0,
+ 84, 101, 120, 116, 117, 114,
+ 101, 70, 95, 77, 83, 0,
+ 77, 105, 99, 114, 111, 115,
+ 111, 102, 116, 32, 40, 82,
+ 41, 32, 72, 76, 83, 76,
+ 32, 83, 104, 97, 100, 101,
+ 114, 32, 67, 111, 109, 112,
+ 105, 108, 101, 114, 32, 49,
+ 48, 46, 49, 0, 73, 83,
+ 71, 78, 116, 0, 0, 0,
+ 3, 0, 0, 0, 8, 0,
+ 0, 0, 80, 0, 0, 0,
+ 0, 0, 0, 0, 1, 0,
+ 0, 0, 3, 0, 0, 0,
+ 0, 0, 0, 0, 15, 0,
+ 0, 0, 92, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0,
+ 0, 0, 3, 0, 0, 0,
+ 1, 0, 0, 0, 3, 3,
+ 0, 0, 100, 0, 0, 0,
+ 0, 0, 0, 0, 10, 0,
+ 0, 0, 1, 0, 0, 0,
+ 2, 0, 0, 0, 1, 1,
+ 0, 0, 83, 86, 95, 80,
+ 79, 83, 73, 84, 73, 79,
+ 78, 0, 84, 69, 88, 67,
+ 79, 82, 68, 0, 83, 86,
+ 95, 83, 65, 77, 80, 76,
+ 69, 73, 78, 68, 69, 88,
+ 0, 171, 79, 83, 71, 78,
+ 44, 0, 0, 0, 1, 0,
+ 0, 0, 8, 0, 0, 0,
+ 32, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0,
+ 3, 0, 0, 0, 0, 0,
+ 0, 0, 15, 0, 0, 0,
+ 83, 86, 95, 84, 65, 82,
+ 71, 69, 84, 0, 171, 171,
+ 83, 72, 68, 82, 168, 0,
+ 0, 0, 65, 0, 0, 0,
+ 42, 0, 0, 0, 106, 8,
+ 0, 1, 88, 32, 0, 4,
+ 0, 112, 16, 0, 0, 0,
+ 0, 0, 85, 85, 0, 0,
+ 98, 16, 0, 3, 50, 16,
+ 16, 0, 1, 0, 0, 0,
+ 99, 8, 0, 4, 18, 16,
+ 16, 0, 2, 0, 0, 0,
+ 10, 0, 0, 0, 101, 0,
+ 0, 3, 242, 32, 16, 0,
+ 0, 0, 0, 0, 104, 0,
+ 0, 2, 1, 0, 0, 0,
+ 28, 0, 0, 5, 50, 0,
+ 16, 0, 0, 0, 0, 0,
+ 70, 16, 16, 0, 1, 0,
+ 0, 0, 54, 0, 0, 8,
+ 194, 0, 16, 0, 0, 0,
+ 0, 0, 2, 64, 0, 0,
+ 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 46, 0,
+ 0, 9, 242, 32, 16, 0,
+ 0, 0, 0, 0, 70, 14,
+ 16, 0, 0, 0, 0, 0,
+ 70, 126, 16, 0, 0, 0,
+ 0, 0, 10, 16, 16, 0,
+ 2, 0, 0, 0, 62, 0,
+ 0, 1, 83, 84, 65, 84,
+ 116, 0, 0, 0, 4, 0,
+ 0, 0, 1, 0, 0, 0,
+ 0, 0, 0, 0, 3, 0,
+ 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0,
+ 0, 0, 1, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 1, 0,
+ 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0,
+ 0, 0, 1, 0, 0, 0,
+ 0, 0, 0, 0, 1, 0,
+ 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0,
+ 0, 0, 0, 0, 0, 0,
+ 0, 0, 1, 0, 0, 0
+};
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/swizzle_format_data.json b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/swizzle_format_data.json
deleted file mode 100644
index 3e9e6877d9..0000000000
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/swizzle_format_data.json
+++ /dev/null
@@ -1,77 +0,0 @@
-{
- "GL_UNSIGNED_NORMALIZED": {
- "8": {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "rtvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM"
- },
- "16": {
- "texFormat": "DXGI_FORMAT_R16G16B16A16_UNORM",
- "srvFormat": "DXGI_FORMAT_R16G16B16A16_UNORM",
- "rtvFormat": "DXGI_FORMAT_R16G16B16A16_UNORM"
- },
- "24": {
- "texFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT",
- "srvFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT",
- "rtvFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT"
- },
- "32": {
- "texFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT",
- "srvFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT",
- "rtvFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT"
- }
- },
- "GL_SIGNED_NORMALIZED": {
- "8": {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_SNORM",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_SNORM",
- "rtvFormat": "DXGI_FORMAT_R8G8B8A8_SNORM"
- }
- },
- "GL_FLOAT": {
- "16": {
- "texFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT",
- "srvFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT",
- "rtvFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT"
- },
- "32": {
- "texFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT",
- "srvFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT",
- "rtvFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT"
- }
- },
- "GL_UNSIGNED_INT": {
- "8": {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_UINT",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_UINT",
- "rtvFormat": "DXGI_FORMAT_R8G8B8A8_UINT"
- },
- "16": {
- "texFormat": "DXGI_FORMAT_R16G16B16A16_UINT",
- "srvFormat": "DXGI_FORMAT_R16G16B16A16_UINT",
- "rtvFormat": "DXGI_FORMAT_R16G16B16A16_UINT"
- },
- "32": {
- "texFormat": "DXGI_FORMAT_R32G32B32A32_UINT",
- "srvFormat": "DXGI_FORMAT_R32G32B32A32_UINT",
- "rtvFormat": "DXGI_FORMAT_R32G32B32A32_UINT"
- }
- },
- "GL_INT": {
- "8": {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_SINT",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_SINT",
- "rtvFormat": "DXGI_FORMAT_R8G8B8A8_SINT"
- },
- "16": {
- "texFormat": "DXGI_FORMAT_R16G16B16A16_SINT",
- "srvFormat": "DXGI_FORMAT_R16G16B16A16_SINT",
- "rtvFormat": "DXGI_FORMAT_R16G16B16A16_SINT"
- },
- "32": {
- "texFormat": "DXGI_FORMAT_R32G32B32A32_SINT",
- "srvFormat": "DXGI_FORMAT_R32G32B32A32_SINT",
- "rtvFormat": "DXGI_FORMAT_R32G32B32A32_SINT"
- }
- }
-} \ No newline at end of file
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/swizzle_format_info.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/swizzle_format_info.h
deleted file mode 100644
index df9a30ff50..0000000000
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/swizzle_format_info.h
+++ /dev/null
@@ -1,51 +0,0 @@
-//
-// Copyright 2015 The ANGLE Project Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-//
-// swizzle_format_info:
-// Provides information for swizzle format and a map from type->formatinfo
-//
-
-#ifndef LIBANGLE_RENDERER_D3D_D3D11_SWIZZLEFORMATINFO_H_
-#define LIBANGLE_RENDERER_D3D_D3D11_SWIZZLEFORMATINFO_H_
-
-#include <GLES2/gl2.h>
-#include <map>
-
-#include "common/platform.h"
-
-namespace rx
-{
-
-namespace d3d11
-{
-
-struct SwizzleSizeType
-{
- size_t maxComponentSize;
- GLenum componentType;
-
- SwizzleSizeType();
- SwizzleSizeType(size_t maxComponentSize, GLenum componentType);
-
- bool operator<(const SwizzleSizeType &other) const;
-};
-
-struct SwizzleFormatInfo
-{
- DXGI_FORMAT mTexFormat;
- DXGI_FORMAT mSRVFormat;
- DXGI_FORMAT mRTVFormat;
-
- SwizzleFormatInfo();
- SwizzleFormatInfo(DXGI_FORMAT texFormat, DXGI_FORMAT srvFormat, DXGI_FORMAT rtvFormat);
-};
-
-const SwizzleFormatInfo &GetSwizzleFormatInfo(GLuint maxBits, GLenum componentType);
-
-} // namespace d3d11
-
-} // namespace rx
-
-#endif // LIBANGLE_RENDERER_D3D_D3D11_SWIZZLEFORMATINFO_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/swizzle_format_info_autogen.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/swizzle_format_info_autogen.cpp
deleted file mode 100644
index 84d6fada97..0000000000
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/swizzle_format_info_autogen.cpp
+++ /dev/null
@@ -1,203 +0,0 @@
-// GENERATED FILE - DO NOT EDIT
-// Generated by gen_swizzle_format_table.py using data from swizzle_format_data.json
-//
-// Copyright 2015 The ANGLE Project Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-//
-// swizzle_format_info:
-// Provides information for swizzle format and a map from type->formatinfo
-//
-
-#include "libANGLE/renderer/d3d/d3d11/swizzle_format_info.h"
-
-#include <GLES3/gl3.h>
-
-namespace rx
-{
-
-namespace d3d11
-{
-
-SwizzleSizeType::SwizzleSizeType() : maxComponentSize(0), componentType(GL_NONE)
-{
-}
-
-SwizzleSizeType::SwizzleSizeType(size_t maxComponentSize, GLenum componentType)
- : maxComponentSize(maxComponentSize), componentType(componentType)
-{
-}
-
-bool SwizzleSizeType::operator<(const SwizzleSizeType &other) const
-{
- return (maxComponentSize != other.maxComponentSize)
- ? (maxComponentSize < other.maxComponentSize)
- : (componentType < other.componentType);
-}
-
-SwizzleFormatInfo::SwizzleFormatInfo()
- : mTexFormat(DXGI_FORMAT_UNKNOWN),
- mSRVFormat(DXGI_FORMAT_UNKNOWN),
- mRTVFormat(DXGI_FORMAT_UNKNOWN)
-{
-}
-
-SwizzleFormatInfo::SwizzleFormatInfo(DXGI_FORMAT texFormat,
- DXGI_FORMAT srvFormat,
- DXGI_FORMAT rtvFormat)
- : mTexFormat(texFormat), mSRVFormat(srvFormat), mRTVFormat(rtvFormat)
-{
-}
-
-const SwizzleFormatInfo &GetSwizzleFormatInfo(GLuint maxBits, GLenum componentType)
-{
- // clang-format off
- switch (componentType)
- {
- case GL_FLOAT:
- {
- switch (maxBits)
- {
- case 16:
- {
- static const SwizzleFormatInfo formatInfo(DXGI_FORMAT_R16G16B16A16_FLOAT,
- DXGI_FORMAT_R16G16B16A16_FLOAT,
- DXGI_FORMAT_R16G16B16A16_FLOAT);
- return formatInfo;
- }
- case 32:
- {
- static const SwizzleFormatInfo formatInfo(DXGI_FORMAT_R32G32B32A32_FLOAT,
- DXGI_FORMAT_R32G32B32A32_FLOAT,
- DXGI_FORMAT_R32G32B32A32_FLOAT);
- return formatInfo;
- }
- default:
- break;
- }
- }
- case GL_INT:
- {
- switch (maxBits)
- {
- case 16:
- {
- static const SwizzleFormatInfo formatInfo(DXGI_FORMAT_R16G16B16A16_SINT,
- DXGI_FORMAT_R16G16B16A16_SINT,
- DXGI_FORMAT_R16G16B16A16_SINT);
- return formatInfo;
- }
- case 32:
- {
- static const SwizzleFormatInfo formatInfo(DXGI_FORMAT_R32G32B32A32_SINT,
- DXGI_FORMAT_R32G32B32A32_SINT,
- DXGI_FORMAT_R32G32B32A32_SINT);
- return formatInfo;
- }
- case 8:
- {
- static const SwizzleFormatInfo formatInfo(DXGI_FORMAT_R8G8B8A8_SINT,
- DXGI_FORMAT_R8G8B8A8_SINT,
- DXGI_FORMAT_R8G8B8A8_SINT);
- return formatInfo;
- }
- default:
- break;
- }
- }
- case GL_SIGNED_NORMALIZED:
- {
- switch (maxBits)
- {
- case 8:
- {
- static const SwizzleFormatInfo formatInfo(DXGI_FORMAT_R8G8B8A8_SNORM,
- DXGI_FORMAT_R8G8B8A8_SNORM,
- DXGI_FORMAT_R8G8B8A8_SNORM);
- return formatInfo;
- }
- default:
- break;
- }
- }
- case GL_UNSIGNED_INT:
- {
- switch (maxBits)
- {
- case 16:
- {
- static const SwizzleFormatInfo formatInfo(DXGI_FORMAT_R16G16B16A16_UINT,
- DXGI_FORMAT_R16G16B16A16_UINT,
- DXGI_FORMAT_R16G16B16A16_UINT);
- return formatInfo;
- }
- case 32:
- {
- static const SwizzleFormatInfo formatInfo(DXGI_FORMAT_R32G32B32A32_UINT,
- DXGI_FORMAT_R32G32B32A32_UINT,
- DXGI_FORMAT_R32G32B32A32_UINT);
- return formatInfo;
- }
- case 8:
- {
- static const SwizzleFormatInfo formatInfo(DXGI_FORMAT_R8G8B8A8_UINT,
- DXGI_FORMAT_R8G8B8A8_UINT,
- DXGI_FORMAT_R8G8B8A8_UINT);
- return formatInfo;
- }
- default:
- break;
- }
- }
- case GL_UNSIGNED_NORMALIZED:
- {
- switch (maxBits)
- {
- case 16:
- {
- static const SwizzleFormatInfo formatInfo(DXGI_FORMAT_R16G16B16A16_UNORM,
- DXGI_FORMAT_R16G16B16A16_UNORM,
- DXGI_FORMAT_R16G16B16A16_UNORM);
- return formatInfo;
- }
- case 24:
- {
- static const SwizzleFormatInfo formatInfo(DXGI_FORMAT_R32G32B32A32_FLOAT,
- DXGI_FORMAT_R32G32B32A32_FLOAT,
- DXGI_FORMAT_R32G32B32A32_FLOAT);
- return formatInfo;
- }
- case 32:
- {
- static const SwizzleFormatInfo formatInfo(DXGI_FORMAT_R32G32B32A32_FLOAT,
- DXGI_FORMAT_R32G32B32A32_FLOAT,
- DXGI_FORMAT_R32G32B32A32_FLOAT);
- return formatInfo;
- }
- case 8:
- {
- static const SwizzleFormatInfo formatInfo(DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM);
- return formatInfo;
- }
- default:
- break;
- }
- }
-
- default:
- {
- static const SwizzleFormatInfo defaultInfo(DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN);
- return defaultInfo;
- }
- }
- // clang-format on
-
-} // GetSwizzleFormatInfo
-
-} // namespace d3d11
-
-} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/texture_format_data.json b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/texture_format_data.json
index 87d303437f..61cd44a62b 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/texture_format_data.json
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/texture_format_data.json
@@ -1,692 +1,523 @@
{
- "GL_ALPHA": [
- {
- "texFormat": "DXGI_FORMAT_A8_UNORM",
- "srvFormat": "DXGI_FORMAT_A8_UNORM",
- "rtvFormat": "DXGI_FORMAT_A8_UNORM",
- "requirementsFcn": "OnlyFL10Plus"
- },
- {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "rtvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "requirementsFcn": "OnlyFL9_3"
- }
- ],
- "GL_ALPHA16F_EXT": [
- {
- "texFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT",
- "srvFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT",
- "rtvFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT"
- }
- ],
- "GL_ALPHA32F_EXT": [
- {
- "texFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT",
- "srvFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT",
- "rtvFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT"
- }
- ],
- "GL_ALPHA8_EXT": [
- {
- "texFormat": "DXGI_FORMAT_A8_UNORM",
- "srvFormat": "DXGI_FORMAT_A8_UNORM",
- "rtvFormat": "DXGI_FORMAT_A8_UNORM",
- "requirementsFcn": "OnlyFL10Plus"
- },
- {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "rtvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "requirementsFcn": "OnlyFL9_3"
- }
- ],
- "GL_BGR5_A1_ANGLEX": [
- {
- "texFormat": "DXGI_FORMAT_B8G8R8A8_UNORM",
- "srvFormat": "DXGI_FORMAT_B8G8R8A8_UNORM",
- "rtvFormat": "DXGI_FORMAT_B8G8R8A8_UNORM"
- }
- ],
- "GL_BGRA4_ANGLEX": [
- {
- "texFormat": "DXGI_FORMAT_B8G8R8A8_UNORM",
- "srvFormat": "DXGI_FORMAT_B8G8R8A8_UNORM",
- "rtvFormat": "DXGI_FORMAT_B8G8R8A8_UNORM"
- }
- ],
- "GL_BGRA8_EXT": [
- {
- "texFormat": "DXGI_FORMAT_B8G8R8A8_UNORM",
- "srvFormat": "DXGI_FORMAT_B8G8R8A8_UNORM",
- "rtvFormat": "DXGI_FORMAT_B8G8R8A8_UNORM"
- }
- ],
- "GL_BGRA_EXT": [
- {
- "texFormat": "DXGI_FORMAT_B8G8R8A8_UNORM",
- "srvFormat": "DXGI_FORMAT_B8G8R8A8_UNORM",
- "rtvFormat": "DXGI_FORMAT_B8G8R8A8_UNORM"
- }
- ],
- "GL_COMPRESSED_R11_EAC": [
- {
- "texFormat": "DXGI_FORMAT_R8_UNORM",
- "srvFormat": "DXGI_FORMAT_R8_UNORM",
- "requirementsFcn": "OnlyFL10Plus"
- }
- ],
- "GL_COMPRESSED_RG11_EAC": [
- {
- "texFormat": "DXGI_FORMAT_R8G8_UNORM",
- "srvFormat": "DXGI_FORMAT_R8G8_UNORM",
- "requirementsFcn": "OnlyFL10Plus"
- }
- ],
- "GL_COMPRESSED_RGB8_ETC2": [
- {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "requirementsFcn": "OnlyFL10Plus"
- }
- ],
- "GL_COMPRESSED_RGB8_PUNCHTHROUGH_ALPHA1_ETC2": [
- {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "requirementsFcn": "OnlyFL10Plus"
- }
- ],
- "GL_COMPRESSED_RGBA8_ETC2_EAC": [
- {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "requirementsFcn": "OnlyFL10Plus"
- }
- ],
- "GL_COMPRESSED_RGBA_S3TC_DXT1_EXT": [
- {
- "texFormat": "DXGI_FORMAT_BC1_UNORM",
- "srvFormat": "DXGI_FORMAT_BC1_UNORM"
- }
- ],
- "GL_COMPRESSED_RGBA_S3TC_DXT3_ANGLE": [
- {
- "texFormat": "DXGI_FORMAT_BC2_UNORM",
- "srvFormat": "DXGI_FORMAT_BC2_UNORM"
- }
- ],
- "GL_COMPRESSED_RGBA_S3TC_DXT5_ANGLE": [
- {
- "texFormat": "DXGI_FORMAT_BC3_UNORM",
- "srvFormat": "DXGI_FORMAT_BC3_UNORM"
- }
- ],
- "GL_COMPRESSED_RGB_S3TC_DXT1_EXT": [
- {
- "texFormat": "DXGI_FORMAT_BC1_UNORM",
- "srvFormat": "DXGI_FORMAT_BC1_UNORM"
- }
- ],
- "GL_COMPRESSED_SIGNED_R11_EAC": [
- {
- "texFormat": "DXGI_FORMAT_R8_SNORM",
- "srvFormat": "DXGI_FORMAT_R8_SNORM",
- "requirementsFcn": "OnlyFL10Plus"
- }
- ],
- "GL_COMPRESSED_SIGNED_RG11_EAC": [
- {
- "texFormat": "DXGI_FORMAT_R8G8_SNORM",
- "srvFormat": "DXGI_FORMAT_R8G8_SNORM",
- "requirementsFcn": "OnlyFL10Plus"
- }
- ],
- "GL_COMPRESSED_SRGB8_ALPHA8_ETC2_EAC": [
- {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_UNORM_SRGB",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM_SRGB",
- "requirementsFcn": "OnlyFL10Plus"
- }
- ],
- "GL_COMPRESSED_SRGB8_ETC2": [
- {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_UNORM_SRGB",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM_SRGB",
- "requirementsFcn": "OnlyFL10Plus"
- }
- ],
- "GL_COMPRESSED_SRGB8_PUNCHTHROUGH_ALPHA1_ETC2": [
- {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_UNORM_SRGB",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM_SRGB",
- "requirementsFcn": "OnlyFL10Plus"
- }
- ],
- "GL_DEPTH24_STENCIL8": [
- {
+ "NONE": {
+ },
+ "A8_UNORM": {
+ "texFormat": "DXGI_FORMAT_A8_UNORM",
+ "srvFormat": "DXGI_FORMAT_A8_UNORM",
+ "rtvFormat": "DXGI_FORMAT_A8_UNORM",
+ "channels": "a",
+ "componentType": "unorm",
+ "bits": { "alpha": 8 },
+ "supportTest": "OnlyFL10Plus(deviceCaps)",
+ "fallbackFormat": "R8G8B8A8_UNORM"
+ },
+ "R8G8B8A8_UNORM": {
+ "texFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
+ "srvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
+ "rtvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
+ "channels": "rgba",
+ "componentType": "unorm",
+ "bits": { "red": 8, "green": 8, "blue": 8, "alpha": 8 },
+ "glInternalFormat": "GL_RGBA8"
+ },
+ "R16G16B16A16_UNORM": {
+ "texFormat": "DXGI_FORMAT_R16G16B16A16_UNORM",
+ "srvFormat": "DXGI_FORMAT_R16G16B16A16_UNORM",
+ "rtvFormat": "DXGI_FORMAT_R16G16B16A16_UNORM",
+ "channels": "rgba",
+ "componentType": "unorm",
+ "bits": { "red": 16, "green": 16, "blue": 16, "alpha": 16 },
+ "glInternalFormat": "GL_RGBA16_EXT"
+ },
+ "R16G16B16A16_FLOAT": {
+ "texFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT",
+ "srvFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT",
+ "rtvFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT",
+ "channels": "rgba",
+ "componentType": "float",
+ "bits": { "red": 16, "green": 16, "blue": 16, "alpha": 16 },
+ "glInternalFormat": "GL_RGBA16F"
+ },
+ "R32G32B32A32_FLOAT": {
+ "texFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT",
+ "srvFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT",
+ "rtvFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT",
+ "channels": "rgba",
+ "componentType": "float",
+ "bits": { "red": 32, "green": 32, "blue": 32, "alpha": 32 },
+ "glInternalFormat": "GL_RGBA32F"
+ },
+ "B8G8R8A8_UNORM": {
+ "texFormat": "DXGI_FORMAT_B8G8R8A8_UNORM",
+ "srvFormat": "DXGI_FORMAT_B8G8R8A8_UNORM",
+ "rtvFormat": "DXGI_FORMAT_B8G8R8A8_UNORM",
+ "channels": "bgra",
+ "componentType": "unorm",
+ "bits": { "red": 8, "green": 8, "blue": 8, "alpha": 8 },
+ "glInternalFormat": "GL_BGRA8_EXT"
+ },
+ "B8G8R8A8_UNORM_SRGB": {
+ "texFormat": "DXGI_FORMAT_B8G8R8A8_UNORM_SRGB",
+ "srvFormat": "DXGI_FORMAT_B8G8R8A8_UNORM_SRGB",
+ "rtvFormat": "DXGI_FORMAT_B8G8R8A8_UNORM_SRGB",
+ "channels": "bgra",
+ "componentType": "unorm",
+ "bits": {"red": 8, "green": 8, "blue": 8,"alpha": 8},
+ "siwzzleFormat": "GL_RGBA8"
+ },
+ "BC1_RGBA_UNORM_BLOCK": {
+ "texFormat": "DXGI_FORMAT_BC1_UNORM",
+ "srvFormat": "DXGI_FORMAT_BC1_UNORM",
+ "channels": "rgba",
+ "componentType": "unorm",
+ "swizzleFormat": "GL_RGBA8"
+ },
+ "BC1_RGB_UNORM_BLOCK": {
+ "texFormat": "DXGI_FORMAT_BC1_UNORM",
+ "srvFormat": "DXGI_FORMAT_BC1_UNORM",
+ "channels": "rgba",
+ "componentType": "unorm",
+ "swizzleFormat": "GL_RGBA8"
+ },
+ "BC2_RGBA_UNORM_BLOCK": {
+ "texFormat": "DXGI_FORMAT_BC2_UNORM",
+ "srvFormat": "DXGI_FORMAT_BC2_UNORM",
+ "channels": "rgba",
+ "componentType": "unorm",
+ "swizzleFormat": "GL_RGBA8"
+ },
+ "BC3_RGBA_UNORM_BLOCK": {
+ "texFormat": "DXGI_FORMAT_BC3_UNORM",
+ "srvFormat": "DXGI_FORMAT_BC3_UNORM",
+ "channels": "rgba",
+ "componentType": "unorm",
+ "swizzleFormat": "GL_RGBA8"
+ },
+ "BC1_RGBA_UNORM_SRGB_BLOCK": {
+ "texFormat": "DXGI_FORMAT_BC1_UNORM_SRGB",
+ "srvFormat": "DXGI_FORMAT_BC1_UNORM_SRGB",
+ "channels": "rgba",
+ "componentType": "unorm",
+ "swizzleFormat": "GL_RGBA8"
+ },
+ "BC1_RGB_UNORM_SRGB_BLOCK": {
+ "texFormat": "DXGI_FORMAT_BC1_UNORM_SRGB",
+ "srvFormat": "DXGI_FORMAT_BC1_UNORM_SRGB",
+ "channels": "rgba",
+ "componentType": "unorm",
+ "swizzleFormat": "GL_RGBA8"
+ },
+ "BC2_RGBA_UNORM_SRGB_BLOCK": {
+ "texFormat": "DXGI_FORMAT_BC2_UNORM_SRGB",
+ "srvFormat": "DXGI_FORMAT_BC2_UNORM_SRGB",
+ "channels": "rgba",
+ "componentType": "unorm",
+ "swizzleFormat": "GL_RGBA8"
+ },
+ "BC3_RGBA_UNORM_SRGB_BLOCK": {
+ "texFormat": "DXGI_FORMAT_BC3_UNORM_SRGB",
+ "srvFormat": "DXGI_FORMAT_BC3_UNORM_SRGB",
+ "channels": "rgba",
+ "componentType": "unorm",
+ "swizzleFormat": "GL_RGBA8"
+ },
+ "D24_UNORM_S8_UINT": {
+ "FL10Plus": {
"texFormat": "DXGI_FORMAT_R24G8_TYPELESS",
- "srvFormat": "DXGI_FORMAT_R24_UNORM_X8_TYPELESS",
- "dsvFormat": "DXGI_FORMAT_D24_UNORM_S8_UINT",
- "requirementsFcn": "OnlyFL10Plus"
+ "srvFormat": "DXGI_FORMAT_R24_UNORM_X8_TYPELESS"
},
- {
- "texFormat": "DXGI_FORMAT_D24_UNORM_S8_UINT",
- "dsvFormat": "DXGI_FORMAT_D24_UNORM_S8_UINT",
- "requirementsFcn": "OnlyFL9_3"
- }
- ],
- "GL_DEPTH32F_STENCIL8": [
- {
- "texFormat": "DXGI_FORMAT_R32G8X24_TYPELESS",
- "srvFormat": "DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS",
- "dsvFormat": "DXGI_FORMAT_D32_FLOAT_S8X24_UINT",
- "requirementsFcn": "OnlyFL10Plus"
+ "FL9_3": {
+ "texFormat": "DXGI_FORMAT_D24_UNORM_S8_UINT"
},
- {
- "requirementsFcn": "OnlyFL9_3"
- }
- ],
- "GL_DEPTH_COMPONENT16": [
- {
+ "dsvFormat": "DXGI_FORMAT_D24_UNORM_S8_UINT",
+ "channels": "ds",
+ "bits": { "depth": 24, "stencil": 8 },
+ "glInternalFormat": "GL_DEPTH24_STENCIL8_OES"
+ },
+ "D32_FLOAT_S8X24_UINT": {
+ "texFormat": "DXGI_FORMAT_R32G8X24_TYPELESS",
+ "srvFormat": "DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS",
+ "dsvFormat": "DXGI_FORMAT_D32_FLOAT_S8X24_UINT",
+ "channels": "ds",
+ "bits": { "depth": 32, "stencil": 8 },
+ "glInternalFormat": "GL_DEPTH32F_STENCIL8"
+ },
+ "D16_UNORM": {
+ "FL10Plus": {
"texFormat": "DXGI_FORMAT_R16_TYPELESS",
- "srvFormat": "DXGI_FORMAT_R16_UNORM",
- "dsvFormat": "DXGI_FORMAT_D16_UNORM",
- "requirementsFcn": "OnlyFL10Plus"
- },
- {
- "texFormat": "DXGI_FORMAT_D16_UNORM",
- "dsvFormat": "DXGI_FORMAT_D16_UNORM",
- "requirementsFcn": "OnlyFL9_3"
- }
- ],
- "GL_DEPTH_COMPONENT24": [
- {
- "texFormat": "DXGI_FORMAT_R24G8_TYPELESS",
- "srvFormat": "DXGI_FORMAT_R24_UNORM_X8_TYPELESS",
- "dsvFormat": "DXGI_FORMAT_D24_UNORM_S8_UINT",
- "requirementsFcn": "OnlyFL10Plus"
- },
- {
- "texFormat": "DXGI_FORMAT_D24_UNORM_S8_UINT",
- "dsvFormat": "DXGI_FORMAT_D24_UNORM_S8_UINT",
- "requirementsFcn": "OnlyFL9_3"
- }
- ],
- "GL_DEPTH_COMPONENT32F": [
- {
- "texFormat": "DXGI_FORMAT_R32_TYPELESS",
- "srvFormat": "DXGI_FORMAT_R32_FLOAT",
- "dsvFormat": "DXGI_FORMAT_D32_FLOAT",
- "requirementsFcn": "OnlyFL10Plus"
+ "srvFormat": "DXGI_FORMAT_R16_UNORM"
},
- {
- "requirementsFcn": "OnlyFL9_3"
- }
- ],
- "GL_DEPTH_COMPONENT32_OES": [
- {
- "texFormat": "DXGI_FORMAT_R24G8_TYPELESS",
- "srvFormat": "DXGI_FORMAT_R24_UNORM_X8_TYPELESS",
- "dsvFormat": "DXGI_FORMAT_D24_UNORM_S8_UINT",
- "requirementsFcn": "OnlyFL10Plus"
- }
- ],
- "GL_ETC1_RGB8_OES": [
- {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM"
- }
- ],
- "GL_ETC1_RGB8_LOSSY_DECODE_ANGLE": [
- {
- "texFormat": "DXGI_FORMAT_BC1_UNORM",
- "srvFormat": "DXGI_FORMAT_BC1_UNORM"
- }
- ],
- "GL_LUMINANCE": [
- {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "rtvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM"
- }
- ],
- "GL_LUMINANCE16F_EXT": [
- {
- "texFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT",
- "srvFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT",
- "rtvFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT"
- }
- ],
- "GL_LUMINANCE32F_EXT": [
- {
- "texFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT",
- "srvFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT",
- "rtvFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT"
- }
- ],
- "GL_LUMINANCE8_ALPHA8_EXT": [
- {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "rtvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM"
- }
- ],
- "GL_LUMINANCE8_EXT": [
- {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "rtvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM"
- }
- ],
- "GL_LUMINANCE_ALPHA": [
- {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "rtvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM"
- }
- ],
- "GL_LUMINANCE_ALPHA16F_EXT": [
- {
- "texFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT",
- "srvFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT",
- "rtvFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT"
- }
- ],
- "GL_LUMINANCE_ALPHA32F_EXT": [
- {
- "texFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT",
- "srvFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT",
- "rtvFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT"
- }
- ],
- "GL_NONE": [
- {
- }
- ],
- "GL_R11F_G11F_B10F": [
- {
- "texFormat": "DXGI_FORMAT_R11G11B10_FLOAT",
- "srvFormat": "DXGI_FORMAT_R11G11B10_FLOAT",
- "rtvFormat": "DXGI_FORMAT_R11G11B10_FLOAT"
- }
- ],
- "GL_R16F": [
- {
- "texFormat": "DXGI_FORMAT_R16_FLOAT",
- "srvFormat": "DXGI_FORMAT_R16_FLOAT",
- "rtvFormat": "DXGI_FORMAT_R16_FLOAT"
- }
- ],
- "GL_R16I": [
- {
- "texFormat": "DXGI_FORMAT_R16_SINT",
- "srvFormat": "DXGI_FORMAT_R16_SINT",
- "rtvFormat": "DXGI_FORMAT_R16_SINT"
- }
- ],
- "GL_R16UI": [
- {
- "texFormat": "DXGI_FORMAT_R16_UINT",
- "srvFormat": "DXGI_FORMAT_R16_UINT",
- "rtvFormat": "DXGI_FORMAT_R16_UINT"
- }
- ],
- "GL_R32F": [
- {
- "texFormat": "DXGI_FORMAT_R32_FLOAT",
- "srvFormat": "DXGI_FORMAT_R32_FLOAT",
- "rtvFormat": "DXGI_FORMAT_R32_FLOAT"
- }
- ],
- "GL_R32I": [
- {
- "texFormat": "DXGI_FORMAT_R32_SINT",
- "srvFormat": "DXGI_FORMAT_R32_SINT",
- "rtvFormat": "DXGI_FORMAT_R32_SINT"
- }
- ],
- "GL_R32UI": [
- {
- "texFormat": "DXGI_FORMAT_R32_UINT",
- "srvFormat": "DXGI_FORMAT_R32_UINT",
- "rtvFormat": "DXGI_FORMAT_R32_UINT"
- }
- ],
- "GL_R8": [
- {
- "texFormat": "DXGI_FORMAT_R8_UNORM",
- "srvFormat": "DXGI_FORMAT_R8_UNORM",
- "rtvFormat": "DXGI_FORMAT_R8_UNORM"
- }
- ],
- "GL_R8I": [
- {
- "texFormat": "DXGI_FORMAT_R8_SINT",
- "srvFormat": "DXGI_FORMAT_R8_SINT",
- "rtvFormat": "DXGI_FORMAT_R8_SINT"
- }
- ],
- "GL_R8UI": [
- {
- "texFormat": "DXGI_FORMAT_R8_UINT",
- "srvFormat": "DXGI_FORMAT_R8_UINT",
- "rtvFormat": "DXGI_FORMAT_R8_UINT"
- }
- ],
- "GL_R8_SNORM": [
- {
- "texFormat": "DXGI_FORMAT_R8_SNORM",
- "srvFormat": "DXGI_FORMAT_R8_SNORM"
- }
- ],
- "GL_RG16F": [
- {
- "texFormat": "DXGI_FORMAT_R16G16_FLOAT",
- "srvFormat": "DXGI_FORMAT_R16G16_FLOAT",
- "rtvFormat": "DXGI_FORMAT_R16G16_FLOAT"
- }
- ],
- "GL_RG16I": [
- {
- "texFormat": "DXGI_FORMAT_R16G16_SINT",
- "srvFormat": "DXGI_FORMAT_R16G16_SINT",
- "rtvFormat": "DXGI_FORMAT_R16G16_SINT"
- }
- ],
- "GL_RG16UI": [
- {
- "texFormat": "DXGI_FORMAT_R16G16_UINT",
- "srvFormat": "DXGI_FORMAT_R16G16_UINT",
- "rtvFormat": "DXGI_FORMAT_R16G16_UINT"
- }
- ],
- "GL_RG32F": [
- {
- "texFormat": "DXGI_FORMAT_R32G32_FLOAT",
- "srvFormat": "DXGI_FORMAT_R32G32_FLOAT",
- "rtvFormat": "DXGI_FORMAT_R32G32_FLOAT"
- }
- ],
- "GL_RG32I": [
- {
- "texFormat": "DXGI_FORMAT_R32G32_SINT",
- "srvFormat": "DXGI_FORMAT_R32G32_SINT",
- "rtvFormat": "DXGI_FORMAT_R32G32_SINT"
- }
- ],
- "GL_RG32UI": [
- {
- "texFormat": "DXGI_FORMAT_R32G32_UINT",
- "srvFormat": "DXGI_FORMAT_R32G32_UINT",
- "rtvFormat": "DXGI_FORMAT_R32G32_UINT"
- }
- ],
- "GL_RG8": [
- {
- "texFormat": "DXGI_FORMAT_R8G8_UNORM",
- "srvFormat": "DXGI_FORMAT_R8G8_UNORM",
- "rtvFormat": "DXGI_FORMAT_R8G8_UNORM"
- }
- ],
- "GL_RG8I": [
- {
- "texFormat": "DXGI_FORMAT_R8G8_SINT",
- "srvFormat": "DXGI_FORMAT_R8G8_SINT",
- "rtvFormat": "DXGI_FORMAT_R8G8_SINT"
- }
- ],
- "GL_RG8UI": [
- {
- "texFormat": "DXGI_FORMAT_R8G8_UINT",
- "srvFormat": "DXGI_FORMAT_R8G8_UINT",
- "rtvFormat": "DXGI_FORMAT_R8G8_UINT"
- }
- ],
- "GL_RG8_SNORM": [
- {
- "texFormat": "DXGI_FORMAT_R8G8_SNORM",
- "srvFormat": "DXGI_FORMAT_R8G8_SNORM"
- }
- ],
- "GL_RGB": [
- {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "rtvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM"
- }
- ],
- "GL_RGB10_A2": [
- {
- "texFormat": "DXGI_FORMAT_R10G10B10A2_UNORM",
- "srvFormat": "DXGI_FORMAT_R10G10B10A2_UNORM",
- "rtvFormat": "DXGI_FORMAT_R10G10B10A2_UNORM"
- }
- ],
- "GL_RGB10_A2UI": [
- {
- "texFormat": "DXGI_FORMAT_R10G10B10A2_UINT",
- "srvFormat": "DXGI_FORMAT_R10G10B10A2_UINT",
- "rtvFormat": "DXGI_FORMAT_R10G10B10A2_UINT"
- }
- ],
- "GL_RGB16F": [
- {
- "texFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT",
- "srvFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT",
- "rtvFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT"
- }
- ],
- "GL_RGB16I": [
- {
- "texFormat": "DXGI_FORMAT_R16G16B16A16_SINT",
- "srvFormat": "DXGI_FORMAT_R16G16B16A16_SINT",
- "rtvFormat": "DXGI_FORMAT_R16G16B16A16_SINT"
- }
- ],
- "GL_RGB16UI": [
- {
- "texFormat": "DXGI_FORMAT_R16G16B16A16_UINT",
- "srvFormat": "DXGI_FORMAT_R16G16B16A16_UINT",
- "rtvFormat": "DXGI_FORMAT_R16G16B16A16_UINT"
- }
- ],
- "GL_RGB32F": [
- {
- "texFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT",
- "srvFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT",
- "rtvFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT"
- }
- ],
- "GL_RGB32I": [
- {
- "texFormat": "DXGI_FORMAT_R32G32B32A32_SINT",
- "srvFormat": "DXGI_FORMAT_R32G32B32A32_SINT",
- "rtvFormat": "DXGI_FORMAT_R32G32B32A32_SINT"
- }
- ],
- "GL_RGB32UI": [
- {
- "texFormat": "DXGI_FORMAT_R32G32B32A32_UINT",
- "srvFormat": "DXGI_FORMAT_R32G32B32A32_UINT",
- "rtvFormat": "DXGI_FORMAT_R32G32B32A32_UINT"
- }
- ],
- "GL_RGB565": [
- {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "rtvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "requirementsFcn": "SupportsFormat<DXGI_FORMAT_B5G6R5_UNORM,false>"
- },
- {
- "texFormat": "DXGI_FORMAT_B5G6R5_UNORM",
- "srvFormat": "DXGI_FORMAT_B5G6R5_UNORM",
- "rtvFormat": "DXGI_FORMAT_B5G6R5_UNORM",
- "requirementsFcn": "SupportsFormat<DXGI_FORMAT_B5G6R5_UNORM,true>"
- }
- ],
- "GL_RGB5_A1": [
- {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "rtvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "requirementsFcn": "SupportsFormat<DXGI_FORMAT_B5G5R5A1_UNORM,false>"
- },
- {
- "texFormat": "DXGI_FORMAT_B5G5R5A1_UNORM",
- "srvFormat": "DXGI_FORMAT_B5G5R5A1_UNORM",
- "rtvFormat": "DXGI_FORMAT_B5G5R5A1_UNORM",
- "requirementsFcn": "SupportsFormat<DXGI_FORMAT_B5G5R5A1_UNORM,true>"
- }
- ],
- "GL_RGB8": [
- {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "rtvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM"
- }
- ],
- "GL_RGB8I": [
- {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_SINT",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_SINT",
- "rtvFormat": "DXGI_FORMAT_R8G8B8A8_SINT"
- }
- ],
- "GL_RGB8UI": [
- {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_UINT",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_UINT",
- "rtvFormat": "DXGI_FORMAT_R8G8B8A8_UINT"
- }
- ],
- "GL_RGB8_SNORM": [
- {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_SNORM",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_SNORM"
- }
- ],
- "GL_RGB9_E5": [
- {
- "texFormat": "DXGI_FORMAT_R9G9B9E5_SHAREDEXP",
- "srvFormat": "DXGI_FORMAT_R9G9B9E5_SHAREDEXP"
- }
- ],
- "GL_RGBA": [
- {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "rtvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM"
- }
- ],
- "GL_RGBA16F": [
- {
- "texFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT",
- "srvFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT",
- "rtvFormat": "DXGI_FORMAT_R16G16B16A16_FLOAT"
- }
- ],
- "GL_RGBA16I": [
- {
- "texFormat": "DXGI_FORMAT_R16G16B16A16_SINT",
- "srvFormat": "DXGI_FORMAT_R16G16B16A16_SINT",
- "rtvFormat": "DXGI_FORMAT_R16G16B16A16_SINT"
- }
- ],
- "GL_RGBA16UI": [
- {
- "texFormat": "DXGI_FORMAT_R16G16B16A16_UINT",
- "srvFormat": "DXGI_FORMAT_R16G16B16A16_UINT",
- "rtvFormat": "DXGI_FORMAT_R16G16B16A16_UINT"
- }
- ],
- "GL_RGBA32F": [
- {
- "texFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT",
- "srvFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT",
- "rtvFormat": "DXGI_FORMAT_R32G32B32A32_FLOAT"
- }
- ],
- "GL_RGBA32I": [
- {
- "texFormat": "DXGI_FORMAT_R32G32B32A32_SINT",
- "srvFormat": "DXGI_FORMAT_R32G32B32A32_SINT",
- "rtvFormat": "DXGI_FORMAT_R32G32B32A32_SINT"
- }
- ],
- "GL_RGBA32UI": [
- {
- "texFormat": "DXGI_FORMAT_R32G32B32A32_UINT",
- "srvFormat": "DXGI_FORMAT_R32G32B32A32_UINT",
- "rtvFormat": "DXGI_FORMAT_R32G32B32A32_UINT"
- }
- ],
- "GL_RGBA4": [
- {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "rtvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "requirementsFcn": "SupportsFormat<DXGI_FORMAT_B4G4R4A4_UNORM,false>"
- },
- {
- "texFormat": "DXGI_FORMAT_B4G4R4A4_UNORM",
- "srvFormat": "DXGI_FORMAT_B4G4R4A4_UNORM",
- "rtvFormat": "DXGI_FORMAT_B4G4R4A4_UNORM",
- "requirementsFcn": "SupportsFormat<DXGI_FORMAT_B4G4R4A4_UNORM,true>"
- }
- ],
- "GL_RGBA8": [
- {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM",
- "rtvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM"
- }
- ],
- "GL_RGBA8I": [
- {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_SINT",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_SINT",
- "rtvFormat": "DXGI_FORMAT_R8G8B8A8_SINT"
- }
- ],
- "GL_RGBA8UI": [
- {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_UINT",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_UINT",
- "rtvFormat": "DXGI_FORMAT_R8G8B8A8_UINT"
- }
- ],
- "GL_RGBA8_SNORM": [
- {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_SNORM",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_SNORM"
- }
- ],
- "GL_SRGB8": [
- {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_UNORM_SRGB",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM_SRGB"
- }
- ],
- "GL_SRGB8_ALPHA8": [
- {
- "texFormat": "DXGI_FORMAT_R8G8B8A8_UNORM_SRGB",
- "srvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM_SRGB",
- "rtvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM_SRGB"
- }
- ],
- "GL_STENCIL_INDEX8": [
- {
- "texFormat": "DXGI_FORMAT_R24G8_TYPELESS",
- "srvFormat": "DXGI_FORMAT_X24_TYPELESS_G8_UINT",
- "dsvFormat": "DXGI_FORMAT_D24_UNORM_S8_UINT",
- "requirementsFcn": "OnlyFL10Plus"
+ "FL9_3": {
+ "texFormat": "DXGI_FORMAT_D16_UNORM"
},
- {
- "texFormat": "DXGI_FORMAT_D24_UNORM_S8_UINT",
- "dsvFormat": "DXGI_FORMAT_D24_UNORM_S8_UINT",
- "requirementsFcn": "OnlyFL9_3"
- }
- ]
+ "dsvFormat": "DXGI_FORMAT_D16_UNORM",
+ "channels": "d",
+ "componentType": "unorm",
+ "bits": { "depth": 16 },
+ "glInternalFormat": "GL_DEPTH_COMPONENT16"
+ },
+ "D32_FLOAT": {
+ "texFormat": "DXGI_FORMAT_R32_TYPELESS",
+ "srvFormat": "DXGI_FORMAT_R32_FLOAT",
+ "dsvFormat": "DXGI_FORMAT_D32_FLOAT",
+ "channels": "d",
+ "componentType": "float",
+ "bits": { "depth": 32 },
+ "glInternalFormat": "GL_DEPTH_COMPONENT32F"
+ },
+ "R11G11B10_FLOAT": {
+ "texFormat": "DXGI_FORMAT_R11G11B10_FLOAT",
+ "srvFormat": "DXGI_FORMAT_R11G11B10_FLOAT",
+ "rtvFormat": "DXGI_FORMAT_R11G11B10_FLOAT",
+ "channels": "rgb",
+ "componentType": "float",
+ "bits": { "red": 11, "green": 11, "blue": 10 },
+ "glInternalFormat": "GL_R11F_G11F_B10F"
+ },
+ "R16_FLOAT": {
+ "texFormat": "DXGI_FORMAT_R16_FLOAT",
+ "srvFormat": "DXGI_FORMAT_R16_FLOAT",
+ "rtvFormat": "DXGI_FORMAT_R16_FLOAT",
+ "channels": "r",
+ "componentType": "float",
+ "bits": { "red": 16 },
+ "glInternalFormat": "GL_R16F"
+ },
+ "R16_SINT": {
+ "texFormat": "DXGI_FORMAT_R16_SINT",
+ "srvFormat": "DXGI_FORMAT_R16_SINT",
+ "rtvFormat": "DXGI_FORMAT_R16_SINT",
+ "channels": "r",
+ "componentType": "int",
+ "bits": { "red": 16 },
+ "glInternalFormat": "GL_R16I"
+ },
+ "R16_UINT": {
+ "texFormat": "DXGI_FORMAT_R16_UINT",
+ "srvFormat": "DXGI_FORMAT_R16_UINT",
+ "rtvFormat": "DXGI_FORMAT_R16_UINT",
+ "channels": "r",
+ "componentType": "uint",
+ "bits": { "red": 16 },
+ "glInternalFormat": "GL_R16UI"
+ },
+ "R32_FLOAT": {
+ "texFormat": "DXGI_FORMAT_R32_FLOAT",
+ "srvFormat": "DXGI_FORMAT_R32_FLOAT",
+ "rtvFormat": "DXGI_FORMAT_R32_FLOAT",
+ "channels": "r",
+ "componentType": "float",
+ "bits": { "red": 32 },
+ "glInternalFormat": "GL_R32F"
+ },
+ "R32_SINT": {
+ "texFormat": "DXGI_FORMAT_R32_SINT",
+ "srvFormat": "DXGI_FORMAT_R32_SINT",
+ "rtvFormat": "DXGI_FORMAT_R32_SINT",
+ "channels": "r",
+ "componentType": "int",
+ "bits": { "red": 32 },
+ "glInternalFormat": "GL_R32I"
+ },
+ "R32_UINT": {
+ "texFormat": "DXGI_FORMAT_R32_UINT",
+ "srvFormat": "DXGI_FORMAT_R32_UINT",
+ "rtvFormat": "DXGI_FORMAT_R32_UINT",
+ "channels": "r",
+ "componentType": "uint",
+ "bits": { "red": 32 },
+ "glInternalFormat": "GL_R32UI"
+ },
+ "R8_UNORM": {
+ "texFormat": "DXGI_FORMAT_R8_UNORM",
+ "srvFormat": "DXGI_FORMAT_R8_UNORM",
+ "rtvFormat": "DXGI_FORMAT_R8_UNORM",
+ "channels": "r",
+ "componentType": "unorm",
+ "bits": { "red": 8 },
+ "glInternalFormat": "GL_R8"
+ },
+ "R8_SINT": {
+ "texFormat": "DXGI_FORMAT_R8_SINT",
+ "srvFormat": "DXGI_FORMAT_R8_SINT",
+ "rtvFormat": "DXGI_FORMAT_R8_SINT",
+ "channels": "r",
+ "componentType": "int",
+ "bits": { "red": 8 },
+ "glInternalFormat": "GL_R8I"
+ },
+ "R8_UINT": {
+ "texFormat": "DXGI_FORMAT_R8_UINT",
+ "srvFormat": "DXGI_FORMAT_R8_UINT",
+ "rtvFormat": "DXGI_FORMAT_R8_UINT",
+ "channels": "r",
+ "componentType": "uint",
+ "bits": { "red": 8 },
+ "glInternalFormat": "GL_R8UI"
+ },
+ "R8_SNORM": {
+ "texFormat": "DXGI_FORMAT_R8_SNORM",
+ "srvFormat": "DXGI_FORMAT_R8_SNORM",
+ "channels": "r",
+ "componentType": "snorm",
+ "bits": { "red": 8 },
+ "glInternalFormat": "GL_R8_SNORM"
+ },
+ "R16G16_FLOAT": {
+ "texFormat": "DXGI_FORMAT_R16G16_FLOAT",
+ "srvFormat": "DXGI_FORMAT_R16G16_FLOAT",
+ "rtvFormat": "DXGI_FORMAT_R16G16_FLOAT",
+ "channels": "rg",
+ "componentType": "float",
+ "bits": { "red": 16, "green": 16 },
+ "glInternalFormat": "GL_RG16F"
+ },
+ "R16G16_SINT": {
+ "texFormat": "DXGI_FORMAT_R16G16_SINT",
+ "srvFormat": "DXGI_FORMAT_R16G16_SINT",
+ "rtvFormat": "DXGI_FORMAT_R16G16_SINT",
+ "channels": "rg",
+ "componentType": "int",
+ "bits": { "red": 16, "green": 16 },
+ "glInternalFormat": "GL_RG16I"
+ },
+ "R16G16_UINT": {
+ "texFormat": "DXGI_FORMAT_R16G16_UINT",
+ "srvFormat": "DXGI_FORMAT_R16G16_UINT",
+ "rtvFormat": "DXGI_FORMAT_R16G16_UINT",
+ "channels": "rg",
+ "componentType": "uint",
+ "bits": { "red": 16, "green": 16 },
+ "glInternalFormat": "GL_RG16UI"
+ },
+ "R32G32_FLOAT": {
+ "texFormat": "DXGI_FORMAT_R32G32_FLOAT",
+ "srvFormat": "DXGI_FORMAT_R32G32_FLOAT",
+ "rtvFormat": "DXGI_FORMAT_R32G32_FLOAT",
+ "channels": "rg",
+ "componentType": "float",
+ "bits": { "red": 32, "green": 32 },
+ "glInternalFormat": "GL_RG32F"
+ },
+ "R32G32_SINT": {
+ "texFormat": "DXGI_FORMAT_R32G32_SINT",
+ "srvFormat": "DXGI_FORMAT_R32G32_SINT",
+ "rtvFormat": "DXGI_FORMAT_R32G32_SINT",
+ "channels": "rg",
+ "componentType": "int",
+ "bits": { "red": 32, "green": 32 },
+ "glInternalFormat": "GL_RG32I"
+ },
+ "R32G32_UINT": {
+ "texFormat": "DXGI_FORMAT_R32G32_UINT",
+ "srvFormat": "DXGI_FORMAT_R32G32_UINT",
+ "rtvFormat": "DXGI_FORMAT_R32G32_UINT",
+ "channels": "rg",
+ "componentType": "uint",
+ "bits": { "red": 32, "green": 32 },
+ "glInternalFormat": "GL_RG32UI"
+ },
+ "R8G8_UNORM": {
+ "texFormat": "DXGI_FORMAT_R8G8_UNORM",
+ "srvFormat": "DXGI_FORMAT_R8G8_UNORM",
+ "rtvFormat": "DXGI_FORMAT_R8G8_UNORM",
+ "channels": "rg",
+ "componentType": "unorm",
+ "bits": { "red": 8, "green": 8 },
+ "glInternalFormat": "GL_RG8"
+ },
+ "R8G8_SINT": {
+ "texFormat": "DXGI_FORMAT_R8G8_SINT",
+ "srvFormat": "DXGI_FORMAT_R8G8_SINT",
+ "rtvFormat": "DXGI_FORMAT_R8G8_SINT",
+ "channels": "rg",
+ "componentType": "int",
+ "bits": { "red": 8, "green": 8 },
+ "glInternalFormat": "GL_RG8I"
+ },
+ "R8G8_UINT": {
+ "texFormat": "DXGI_FORMAT_R8G8_UINT",
+ "srvFormat": "DXGI_FORMAT_R8G8_UINT",
+ "rtvFormat": "DXGI_FORMAT_R8G8_UINT",
+ "channels": "rg",
+ "componentType": "uint",
+ "bits": { "red": 8, "green": 8 },
+ "glInternalFormat": "GL_RG8UI"
+ },
+ "R8G8_SNORM": {
+ "texFormat": "DXGI_FORMAT_R8G8_SNORM",
+ "srvFormat": "DXGI_FORMAT_R8G8_SNORM",
+ "channels": "rg",
+ "componentType": "snorm",
+ "bits": { "red": 8, "green": 8 },
+ "glInternalFormat": "GL_RG8_SNORM"
+ },
+ "R10G10B10A2_UNORM": {
+ "texFormat": "DXGI_FORMAT_R10G10B10A2_UNORM",
+ "srvFormat": "DXGI_FORMAT_R10G10B10A2_UNORM",
+ "rtvFormat": "DXGI_FORMAT_R10G10B10A2_UNORM",
+ "channels": "rgba",
+ "componentType": "unorm",
+ "bits": { "red": 10, "green": 10, "blue": 10, "alpha": 2 },
+ "glInternalFormat": "GL_RGB10_A2"
+ },
+ "R10G10B10A2_UINT": {
+ "texFormat": "DXGI_FORMAT_R10G10B10A2_UINT",
+ "srvFormat": "DXGI_FORMAT_R10G10B10A2_UINT",
+ "rtvFormat": "DXGI_FORMAT_R10G10B10A2_UINT",
+ "channels": "rgba",
+ "componentType": "uint",
+ "bits": { "red": 10, "green": 10, "blue": 10, "alpha": 2 },
+ "glInternalFormat": "GL_RGB10_A2UI"
+ },
+ "R16G16B16A16_SINT": {
+ "texFormat": "DXGI_FORMAT_R16G16B16A16_SINT",
+ "srvFormat": "DXGI_FORMAT_R16G16B16A16_SINT",
+ "rtvFormat": "DXGI_FORMAT_R16G16B16A16_SINT",
+ "channels": "rgba",
+ "componentType": "int",
+ "bits": { "red": 16, "green": 16, "blue": 16, "alpha": 16 },
+ "glInternalFormat": "GL_RGBA16I"
+ },
+ "R16G16B16A16_UINT": {
+ "texFormat": "DXGI_FORMAT_R16G16B16A16_UINT",
+ "srvFormat": "DXGI_FORMAT_R16G16B16A16_UINT",
+ "rtvFormat": "DXGI_FORMAT_R16G16B16A16_UINT",
+ "channels": "rgba",
+ "componentType": "uint",
+ "bits": { "red": 16, "green": 16, "blue": 16, "alpha": 16 },
+ "glInternalFormat": "GL_RGBA16UI"
+ },
+ "R32G32B32A32_SINT": {
+ "texFormat": "DXGI_FORMAT_R32G32B32A32_SINT",
+ "srvFormat": "DXGI_FORMAT_R32G32B32A32_SINT",
+ "rtvFormat": "DXGI_FORMAT_R32G32B32A32_SINT",
+ "channels": "rgba",
+ "componentType": "int",
+ "bits": { "red": 32, "green": 32, "blue": 32, "alpha": 32 },
+ "glInternalFormat": "GL_RGBA32I"
+ },
+ "R32G32B32A32_UINT": {
+ "texFormat": "DXGI_FORMAT_R32G32B32A32_UINT",
+ "srvFormat": "DXGI_FORMAT_R32G32B32A32_UINT",
+ "rtvFormat": "DXGI_FORMAT_R32G32B32A32_UINT",
+ "channels": "rgba",
+ "componentType": "uint",
+ "bits": { "red": 32, "green": 32, "blue": 32, "alpha": 32 },
+ "glInternalFormat": "GL_RGBA32UI"
+ },
+ "B5G6R5_UNORM": {
+ "texFormat": "DXGI_FORMAT_B5G6R5_UNORM",
+ "srvFormat": "DXGI_FORMAT_B5G6R5_UNORM",
+ "rtvFormat": "DXGI_FORMAT_B5G6R5_UNORM",
+ "channels": "bgr",
+ "componentType": "unorm",
+ "bits": { "red": 5, "green": 6, "blue": 5 },
+ "supportTest": "SupportsFormat(DXGI_FORMAT_B5G6R5_UNORM, deviceCaps)",
+ "fallbackFormat": "R8G8B8A8_UNORM"
+ },
+ "B5G5R5A1_UNORM": {
+ "texFormat": "DXGI_FORMAT_B5G5R5A1_UNORM",
+ "srvFormat": "DXGI_FORMAT_B5G5R5A1_UNORM",
+ "rtvFormat": "DXGI_FORMAT_B5G5R5A1_UNORM",
+ "channels": "bgra",
+ "componentType": "unorm",
+ "bits": { "red": 5, "green": 5, "blue": 5, "alpha": 1 },
+ "supportTest": "SupportsFormat(DXGI_FORMAT_B5G5R5A1_UNORM, deviceCaps)",
+ "fallbackFormat": "R8G8B8A8_UNORM"
+ },
+ "R8G8B8A8_SINT": {
+ "texFormat": "DXGI_FORMAT_R8G8B8A8_SINT",
+ "srvFormat": "DXGI_FORMAT_R8G8B8A8_SINT",
+ "rtvFormat": "DXGI_FORMAT_R8G8B8A8_SINT",
+ "channels": "rgba",
+ "componentType": "int",
+ "bits": { "red": 8, "green": 8, "blue": 8, "alpha": 8 },
+ "glInternalFormat": "GL_RGBA8I"
+ },
+ "R8G8B8A8_UINT": {
+ "texFormat": "DXGI_FORMAT_R8G8B8A8_UINT",
+ "srvFormat": "DXGI_FORMAT_R8G8B8A8_UINT",
+ "rtvFormat": "DXGI_FORMAT_R8G8B8A8_UINT",
+ "channels": "rgba",
+ "componentType": "uint",
+ "bits": { "red": 8, "green": 8, "blue": 8, "alpha": 8 },
+ "glInternalFormat": "GL_RGBA8UI"
+ },
+ "R8G8B8A8_SNORM": {
+ "texFormat": "DXGI_FORMAT_R8G8B8A8_SNORM",
+ "srvFormat": "DXGI_FORMAT_R8G8B8A8_SNORM",
+ "channels": "rgba",
+ "componentType": "snorm",
+ "bits": { "red": 8, "green": 8, "blue": 8, "alpha": 8 },
+ "glInternalFormat": "GL_RGBA8_SNORM"
+ },
+ "R9G9B9E5_SHAREDEXP": {
+ "texFormat": "DXGI_FORMAT_R9G9B9E5_SHAREDEXP",
+ "srvFormat": "DXGI_FORMAT_R9G9B9E5_SHAREDEXP",
+ "channels": "rgb",
+ "componentType": "float",
+ "bits": { "red": 9, "green": 9, "blue": 9, "shared": 5 }
+ },
+ "B4G4R4A4_UNORM": {
+ "texFormat": "DXGI_FORMAT_B4G4R4A4_UNORM",
+ "srvFormat": "DXGI_FORMAT_B4G4R4A4_UNORM",
+ "rtvFormat": "DXGI_FORMAT_B4G4R4A4_UNORM",
+ "channels": "bgra",
+ "componentType": "unorm",
+ "bits": { "red": 4, "green": 4, "blue": 4, "alpha": 4 },
+ "supportTest": "SupportsFormat(DXGI_FORMAT_B4G4R4A4_UNORM, deviceCaps)",
+ "fallbackFormat": "R8G8B8A8_UNORM"
+ },
+ "R8G8B8A8_UNORM_SRGB": {
+ "texFormat": "DXGI_FORMAT_R8G8B8A8_UNORM_SRGB",
+ "srvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM_SRGB",
+ "rtvFormat": "DXGI_FORMAT_R8G8B8A8_UNORM_SRGB",
+ "channels": "rgba",
+ "componentType": "unorm",
+ "bits": { "red": 8, "green": 8, "blue": 8, "alpha": 8 },
+ "glInternalFormat": "GL_SRGB8_ALPHA8"
+ },
+ "R16_UNORM": {
+ "texFormat": "DXGI_FORMAT_R16_UNORM",
+ "srvFormat": "DXGI_FORMAT_R16_UNORM",
+ "rtvFormat": "DXGI_FORMAT_R16_UNORM",
+ "channels": "r",
+ "componentType": "unorm",
+ "bits": { "red": 16 },
+ "glInternalFormat": "GL_R16_EXT"
+ },
+ "R16G16_UNORM": {
+ "texFormat": "DXGI_FORMAT_R16G16_UNORM",
+ "srvFormat": "DXGI_FORMAT_R16G16_UNORM",
+ "rtvFormat": "DXGI_FORMAT_R16G16_UNORM",
+ "channels": "rg",
+ "componentType": "unorm",
+ "bits": { "red": 16, "green": 16 },
+ "glInternalFormat": "GL_RG16_EXT"
+ },
+ "R16_SNORM": {
+ "texFormat": "DXGI_FORMAT_R16_SNORM",
+ "srvFormat": "DXGI_FORMAT_R16_SNORM",
+ "channels": "r",
+ "componentType": "snorm",
+ "bits": { "red": 16 },
+ "glInternalFormat": "GL_R16_SNORM_EXT"
+ },
+ "R16G16_SNORM": {
+ "texFormat": "DXGI_FORMAT_R16G16_SNORM",
+ "srvFormat": "DXGI_FORMAT_R16G16_SNORM",
+ "channels": "rg",
+ "componentType": "snorm",
+ "bits": { "red": 16, "green": 16 },
+ "glInternalFormat": "GL_RG16_SNORM_EXT"
+ },
+ "R16G16B16A16_SNORM": {
+ "texFormat": "DXGI_FORMAT_R16G16B16A16_SNORM",
+ "srvFormat": "DXGI_FORMAT_R16G16B16A16_SNORM",
+ "channels": "rgba",
+ "componentType": "snorm",
+ "bits": { "red": 16, "green": 16, "blue": 16, "alpha": 16 },
+ "glInternalFormat": "GL_RGBA16_SNORM_EXT"
+ }
}
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/texture_format_map.json b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/texture_format_map.json
new file mode 100644
index 0000000000..3ef2355645
--- /dev/null
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/texture_format_map.json
@@ -0,0 +1,78 @@
+{
+ "GL_ALPHA16F_EXT": "R16G16B16A16_FLOAT",
+ "GL_ALPHA32F_EXT": "R32G32B32A32_FLOAT",
+ "GL_BGR5_A1_ANGLEX": "B8G8R8A8_UNORM",
+ "GL_BGRA4_ANGLEX": "B8G8R8A8_UNORM",
+ "GL_BGRA8_SRGB_ANGLEX": "B8G8R8A8_UNORM_SRGB",
+ "GL_COMPRESSED_R11_EAC": "R8_UNORM",
+ "GL_COMPRESSED_RG11_EAC": "R8G8_UNORM",
+ "GL_COMPRESSED_RGB8_ETC2": "R8G8B8A8_UNORM",
+ "GL_COMPRESSED_RGB8_PUNCHTHROUGH_ALPHA1_ETC2": "R8G8B8A8_UNORM",
+ "GL_COMPRESSED_RGBA8_ETC2_EAC": "R8G8B8A8_UNORM",
+ "GL_COMPRESSED_RGBA_ASTC_4x4_KHR": "NONE",
+ "GL_COMPRESSED_RGBA_ASTC_5x4_KHR": "NONE",
+ "GL_COMPRESSED_RGBA_ASTC_5x5_KHR": "NONE",
+ "GL_COMPRESSED_RGBA_ASTC_6x5_KHR": "NONE",
+ "GL_COMPRESSED_RGBA_ASTC_6x6_KHR": "NONE",
+ "GL_COMPRESSED_RGBA_ASTC_8x5_KHR": "NONE",
+ "GL_COMPRESSED_RGBA_ASTC_8x6_KHR": "NONE",
+ "GL_COMPRESSED_RGBA_ASTC_8x8_KHR": "NONE",
+ "GL_COMPRESSED_RGBA_ASTC_10x5_KHR": "NONE",
+ "GL_COMPRESSED_RGBA_ASTC_10x6_KHR": "NONE",
+ "GL_COMPRESSED_RGBA_ASTC_10x8_KHR": "NONE",
+ "GL_COMPRESSED_RGBA_ASTC_10x10_KHR": "NONE",
+ "GL_COMPRESSED_RGBA_ASTC_12x10_KHR": "NONE",
+ "GL_COMPRESSED_RGBA_ASTC_12x12_KHR": "NONE",
+ "GL_COMPRESSED_SIGNED_R11_EAC": "R8_SNORM",
+ "GL_COMPRESSED_SIGNED_RG11_EAC": "R8G8_SNORM",
+ "GL_COMPRESSED_SRGB8_ALPHA8_ASTC_4x4_KHR": "NONE",
+ "GL_COMPRESSED_SRGB8_ALPHA8_ASTC_5x4_KHR": "NONE",
+ "GL_COMPRESSED_SRGB8_ALPHA8_ASTC_5x5_KHR": "NONE",
+ "GL_COMPRESSED_SRGB8_ALPHA8_ASTC_6x5_KHR": "NONE",
+ "GL_COMPRESSED_SRGB8_ALPHA8_ASTC_6x6_KHR": "NONE",
+ "GL_COMPRESSED_SRGB8_ALPHA8_ASTC_8x5_KHR": "NONE",
+ "GL_COMPRESSED_SRGB8_ALPHA8_ASTC_8x6_KHR": "NONE",
+ "GL_COMPRESSED_SRGB8_ALPHA8_ASTC_8x8_KHR": "NONE",
+ "GL_COMPRESSED_SRGB8_ALPHA8_ASTC_10x5_KHR": "NONE",
+ "GL_COMPRESSED_SRGB8_ALPHA8_ASTC_10x6_KHR": "NONE",
+ "GL_COMPRESSED_SRGB8_ALPHA8_ASTC_10x8_KHR": "NONE",
+ "GL_COMPRESSED_SRGB8_ALPHA8_ASTC_10x10_KHR": "NONE",
+ "GL_COMPRESSED_SRGB8_ALPHA8_ASTC_12x10_KHR": "NONE",
+ "GL_COMPRESSED_SRGB8_ALPHA8_ASTC_12x12_KHR": "NONE",
+ "GL_COMPRESSED_SRGB8_ALPHA8_ETC2_EAC": "R8G8B8A8_UNORM_SRGB",
+ "GL_COMPRESSED_SRGB8_ETC2": "R8G8B8A8_UNORM_SRGB",
+ "GL_COMPRESSED_SRGB8_PUNCHTHROUGH_ALPHA1_ETC2": "R8G8B8A8_UNORM_SRGB",
+ "GL_DEPTH_COMPONENT24": "D24_UNORM_S8_UINT",
+ "GL_DEPTH_COMPONENT32_OES": "D24_UNORM_S8_UINT",
+ "GL_ETC1_RGB8_OES": "R8G8B8A8_UNORM",
+ "GL_ETC1_RGB8_LOSSY_DECODE_ANGLE": "BC1_RGB_UNORM_BLOCK",
+ "GL_COMPRESSED_RGB8_LOSSY_DECODE_ETC2_ANGLE": "BC1_RGB_UNORM_BLOCK",
+ "GL_COMPRESSED_SRGB8_LOSSY_DECODE_ETC2_ANGLE": "BC1_RGB_UNORM_SRGB_BLOCK",
+ "GL_COMPRESSED_RGB8_PUNCHTHROUGH_ALPHA1_LOSSY_DECODE_ETC2_ANGLE": "BC1_RGBA_UNORM_BLOCK",
+ "GL_COMPRESSED_SRGB8_PUNCHTHROUGH_ALPHA1_LOSSY_DECODE_ETC2_ANGLE": "BC1_RGBA_UNORM_SRGB_BLOCK",
+ "GL_LUMINANCE16F_EXT": "R16G16B16A16_FLOAT",
+ "GL_LUMINANCE32F_EXT": "R32G32B32A32_FLOAT",
+ "GL_LUMINANCE8_ALPHA8_EXT": "R8G8B8A8_UNORM",
+ "GL_LUMINANCE8_EXT": "R8G8B8A8_UNORM",
+ "GL_LUMINANCE_ALPHA16F_EXT": "R16G16B16A16_FLOAT",
+ "GL_LUMINANCE_ALPHA32F_EXT": "R32G32B32A32_FLOAT",
+ "GL_RGB": "R8G8B8A8_UNORM",
+ "GL_RGB16F": "R16G16B16A16_FLOAT",
+ "GL_RGB16I": "R16G16B16A16_SINT",
+ "GL_RGB16UI": "R16G16B16A16_UINT",
+ "GL_RGB565": "B5G6R5_UNORM",
+ "GL_RGB5_A1": "B5G5R5A1_UNORM",
+ "GL_RGB8": "R8G8B8A8_UNORM",
+ "GL_RGB8I": "R8G8B8A8_SINT",
+ "GL_RGB8UI": "R8G8B8A8_UINT",
+ "GL_RGB8_SNORM": "R8G8B8A8_SNORM",
+ "GL_RGBA4": "B4G4R4A4_UNORM",
+ "GL_SRGB8": "R8G8B8A8_UNORM_SRGB",
+ "GL_STENCIL_INDEX8": "D24_UNORM_S8_UINT",
+ "GL_RGB16_EXT": "R16G16B16A16_UNORM",
+ "GL_RGBA16_EXT": "R16G16B16A16_UNORM",
+ "GL_RGB16_SNORM_EXT": "R16G16B16A16_SNORM",
+ "GL_RGB32F": "R32G32B32A32_FLOAT",
+ "GL_RGB32I": "R32G32B32A32_SINT",
+ "GL_RGB32UI": "R32G32B32A32_UINT"
+}
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/texture_format_table.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/texture_format_table.cpp
new file mode 100644
index 0000000000..a9dfec56b8
--- /dev/null
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/texture_format_table.cpp
@@ -0,0 +1,35 @@
+//
+// Copyright 2016 The ANGLE Project Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+//
+// Helper routines for the D3D11 texture format table.
+
+#include "libANGLE/renderer/d3d/d3d11/texture_format_table.h"
+
+#include "libANGLE/renderer/load_functions_table.h"
+
+namespace rx
+{
+
+namespace d3d11
+{
+
+const Format &Format::getSwizzleFormat(const Renderer11DeviceCaps &deviceCaps) const
+{
+ return (swizzleFormat == internalFormat ? *this : Format::Get(swizzleFormat, deviceCaps));
+}
+
+LoadFunctionMap Format::getLoadFunctions() const
+{
+ return GetLoadFunctionsMap(internalFormat, formatID);
+}
+
+const angle::Format &Format::format() const
+{
+ return angle::Format::Get(formatID);
+}
+
+} // namespace d3d11
+
+} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/texture_format_table.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/texture_format_table.h
index 1606a28a73..3efcb81adb 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/texture_format_table.h
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/texture_format_table.h
@@ -12,50 +12,91 @@
#include <map>
+#include "common/angleutils.h"
#include "common/platform.h"
+#include "libANGLE/renderer/Format.h"
+#include "libANGLE/renderer/renderer_utils.h"
#include "libANGLE/renderer/d3d/formatutilsD3D.h"
-#include "libANGLE/renderer/d3d/d3d11/Renderer11.h"
namespace rx
{
-namespace d3d11
-{
+struct Renderer11DeviceCaps;
-struct LoadImageFunctionInfo
+namespace d3d11
{
- LoadImageFunctionInfo() : loadFunction(nullptr), requiresConversion(false) {}
- LoadImageFunctionInfo(LoadImageFunction loadFunction, bool requiresConversion)
- : loadFunction(loadFunction), requiresConversion(requiresConversion)
- {
- }
-
- LoadImageFunction loadFunction;
- bool requiresConversion;
-};
-struct TextureFormat
+// For sized GL internal formats, there are several possible corresponding D3D11 formats depending
+// on device capabilities.
+// This structure allows querying for the DXGI texture formats to use for textures, SRVs, RTVs and
+// DSVs given a GL internal format.
+struct Format final : private angle::NonCopyable
{
- TextureFormat();
+ constexpr Format();
+ constexpr Format(GLenum internalFormat,
+ angle::Format::ID formatID,
+ DXGI_FORMAT texFormat,
+ DXGI_FORMAT srvFormat,
+ DXGI_FORMAT rtvFormat,
+ DXGI_FORMAT dsvFormat,
+ DXGI_FORMAT blitSRVFormat,
+ GLenum swizzleFormat,
+ InitializeTextureDataFunction internalFormatInitializer);
+
+ static const Format &Get(GLenum internalFormat, const Renderer11DeviceCaps &deviceCaps);
+
+ const Format &getSwizzleFormat(const Renderer11DeviceCaps &deviceCaps) const;
+ LoadFunctionMap getLoadFunctions() const;
+ const angle::Format &format() const;
+
+ GLenum internalFormat;
+ angle::Format::ID formatID;
DXGI_FORMAT texFormat;
DXGI_FORMAT srvFormat;
DXGI_FORMAT rtvFormat;
DXGI_FORMAT dsvFormat;
- DXGI_FORMAT renderFormat;
- DXGI_FORMAT swizzleTexFormat;
- DXGI_FORMAT swizzleSRVFormat;
- DXGI_FORMAT swizzleRTVFormat;
+ DXGI_FORMAT blitSRVFormat;
- InitializeTextureDataFunction dataInitializerFunction;
- typedef std::map<GLenum, LoadImageFunctionInfo> LoadFunctionMap;
+ GLenum swizzleFormat;
- LoadFunctionMap loadFunctions;
+ InitializeTextureDataFunction dataInitializerFunction;
};
-const TextureFormat &GetTextureFormatInfo(GLenum internalformat,
- const Renderer11DeviceCaps &renderer11DeviceCaps);
+constexpr Format::Format()
+ : internalFormat(GL_NONE),
+ formatID(angle::Format::ID::NONE),
+ texFormat(DXGI_FORMAT_UNKNOWN),
+ srvFormat(DXGI_FORMAT_UNKNOWN),
+ rtvFormat(DXGI_FORMAT_UNKNOWN),
+ dsvFormat(DXGI_FORMAT_UNKNOWN),
+ blitSRVFormat(DXGI_FORMAT_UNKNOWN),
+ swizzleFormat(GL_NONE),
+ dataInitializerFunction(nullptr)
+{
+}
+
+constexpr Format::Format(GLenum internalFormat,
+ angle::Format::ID formatID,
+ DXGI_FORMAT texFormat,
+ DXGI_FORMAT srvFormat,
+ DXGI_FORMAT rtvFormat,
+ DXGI_FORMAT dsvFormat,
+ DXGI_FORMAT blitSRVFormat,
+ GLenum swizzleFormat,
+ InitializeTextureDataFunction internalFormatInitializer)
+ : internalFormat(internalFormat),
+ formatID(formatID),
+ texFormat(texFormat),
+ srvFormat(srvFormat),
+ rtvFormat(rtvFormat),
+ dsvFormat(dsvFormat),
+ blitSRVFormat(blitSRVFormat),
+ swizzleFormat(swizzleFormat),
+ dataInitializerFunction(internalFormatInitializer)
+{
+}
} // namespace d3d11
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/texture_format_table_autogen.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/texture_format_table_autogen.cpp
index 0b214c9756..3c1c2bcd50 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/texture_format_table_autogen.cpp
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/texture_format_table_autogen.cpp
@@ -1,7 +1,7 @@
// GENERATED FILE - DO NOT EDIT.
// Generated by gen_texture_format_table.py using data from texture_format_data.json
//
-// Copyright 2015 The ANGLE Project Authors. All rights reserved.
+// Copyright 2017 The ANGLE Project Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
//
@@ -11,12 +11,15 @@
#include "libANGLE/renderer/d3d/d3d11/texture_format_table.h"
+#include "image_util/copyimage.h"
+#include "image_util/generatemip.h"
+#include "image_util/loadimage.h"
+
#include "libANGLE/renderer/d3d/d3d11/formatutils11.h"
-#include "libANGLE/renderer/d3d/d3d11/internal_format_initializer_table.h"
-#include "libANGLE/renderer/d3d/d3d11/load_functions_table.h"
#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
-#include "libANGLE/renderer/d3d/d3d11/swizzle_format_info.h"
-#include "libANGLE/renderer/d3d/loadimage.h"
+#include "libANGLE/renderer/d3d/d3d11/texture_format_table_utils.h"
+
+using namespace angle;
namespace rx
{
@@ -24,1756 +27,1899 @@ namespace rx
namespace d3d11
{
-namespace
-{
-
-typedef bool (*FormatSupportFunction)(const Renderer11DeviceCaps &);
-
-bool AnyDevice(const Renderer11DeviceCaps &deviceCaps)
-{
- return true;
-}
-
-bool OnlyFL10Plus(const Renderer11DeviceCaps &deviceCaps)
-{
- return (deviceCaps.featureLevel >= D3D_FEATURE_LEVEL_10_0);
-}
-
-bool OnlyFL9_3(const Renderer11DeviceCaps &deviceCaps)
-{
- return (deviceCaps.featureLevel == D3D_FEATURE_LEVEL_9_3);
-}
-
-template <DXGI_FORMAT format, bool requireSupport>
-bool SupportsFormat(const Renderer11DeviceCaps &deviceCaps)
-{
- // Must support texture, SRV and RTV support
- UINT mustSupport = D3D11_FORMAT_SUPPORT_TEXTURE2D | D3D11_FORMAT_SUPPORT_TEXTURECUBE |
- D3D11_FORMAT_SUPPORT_SHADER_SAMPLE | D3D11_FORMAT_SUPPORT_MIP |
- D3D11_FORMAT_SUPPORT_RENDER_TARGET;
-
- if (d3d11_gl::GetMaximumClientVersion(deviceCaps.featureLevel) > 2)
- {
- mustSupport |= D3D11_FORMAT_SUPPORT_TEXTURE3D;
- }
-
- bool fullSupport = false;
- if (format == DXGI_FORMAT_B5G6R5_UNORM)
- {
- // All hardware that supports DXGI_FORMAT_B5G6R5_UNORM should support autogen mipmaps, but
- // check anyway.
- mustSupport |= D3D11_FORMAT_SUPPORT_MIP_AUTOGEN;
- fullSupport = ((deviceCaps.B5G6R5support & mustSupport) == mustSupport);
- }
- else if (format == DXGI_FORMAT_B4G4R4A4_UNORM)
- {
- fullSupport = ((deviceCaps.B4G4R4A4support & mustSupport) == mustSupport);
- }
- else if (format == DXGI_FORMAT_B5G5R5A1_UNORM)
- {
- fullSupport = ((deviceCaps.B5G5R5A1support & mustSupport) == mustSupport);
- }
- else
- {
- UNREACHABLE();
- return false;
- }
-
- // This 'SupportsFormat' function is used by individual entries in the D3D11 Format Map below,
- // which maps GL formats to DXGI formats.
- if (requireSupport)
- {
- // This means that ANGLE would like to use the entry in the map if the inputted DXGI format
- // *IS* supported.
- // e.g. the entry might map GL_RGB5_A1 to DXGI_FORMAT_B5G5R5A1, which should only be used if
- // DXGI_FORMAT_B5G5R5A1 is supported.
- // In this case, we should only return 'true' if the format *IS* supported.
- return fullSupport;
- }
- else
- {
- // This means that ANGLE would like to use the entry in the map if the inputted DXGI format
- // *ISN'T* supported.
- // This might be a fallback entry. e.g. for ANGLE to use DXGI_FORMAT_R8G8B8A8_UNORM if
- // DXGI_FORMAT_B5G5R5A1 isn't supported.
- // In this case, we should only return 'true' if the format *ISN'T* supported.
- return !fullSupport;
- }
-}
-
-// End Format Support Functions
-
-// For sized GL internal formats, there are several possible corresponding D3D11 formats depending
-// on device capabilities.
-// This function allows querying for the DXGI texture formats to use for textures, SRVs, RTVs and
-// DSVs given a GL internal format.
-const TextureFormat GetD3D11FormatInfo(GLenum internalFormat,
- DXGI_FORMAT texFormat,
- DXGI_FORMAT srvFormat,
- DXGI_FORMAT rtvFormat,
- DXGI_FORMAT dsvFormat)
-{
- TextureFormat info;
- info.texFormat = texFormat;
- info.srvFormat = srvFormat;
- info.rtvFormat = rtvFormat;
- info.dsvFormat = dsvFormat;
-
- // Given a GL internal format, the renderFormat is the DSV format if it is depth- or
- // stencil-renderable,
- // the RTV format if it is color-renderable, and the (nonrenderable) texture format otherwise.
- if (dsvFormat != DXGI_FORMAT_UNKNOWN)
- {
- info.renderFormat = dsvFormat;
- }
- else if (rtvFormat != DXGI_FORMAT_UNKNOWN)
- {
- info.renderFormat = rtvFormat;
- }
- else if (texFormat != DXGI_FORMAT_UNKNOWN)
- {
- info.renderFormat = texFormat;
- }
- else
- {
- info.renderFormat = DXGI_FORMAT_UNKNOWN;
- }
-
- // Compute the swizzle formats
- const gl::InternalFormat &formatInfo = gl::GetInternalFormatInfo(internalFormat);
- if (internalFormat != GL_NONE && formatInfo.pixelBytes > 0)
- {
- if (formatInfo.componentCount != 4 || texFormat == DXGI_FORMAT_UNKNOWN ||
- srvFormat == DXGI_FORMAT_UNKNOWN || rtvFormat == DXGI_FORMAT_UNKNOWN)
- {
- // Get the maximum sized component
- unsigned int maxBits = 1;
- if (formatInfo.compressed)
- {
- unsigned int compressedBitsPerBlock = formatInfo.pixelBytes * 8;
- unsigned int blockSize =
- formatInfo.compressedBlockWidth * formatInfo.compressedBlockHeight;
- maxBits = std::max(compressedBitsPerBlock / blockSize, maxBits);
- }
- else
- {
- maxBits = std::max(maxBits, formatInfo.alphaBits);
- maxBits = std::max(maxBits, formatInfo.redBits);
- maxBits = std::max(maxBits, formatInfo.greenBits);
- maxBits = std::max(maxBits, formatInfo.blueBits);
- maxBits = std::max(maxBits, formatInfo.luminanceBits);
- maxBits = std::max(maxBits, formatInfo.depthBits);
- }
-
- maxBits = roundUp(maxBits, 8U);
-
- const SwizzleFormatInfo &swizzleInfo =
- GetSwizzleFormatInfo(maxBits, formatInfo.componentType);
- info.swizzleTexFormat = swizzleInfo.mTexFormat;
- info.swizzleSRVFormat = swizzleInfo.mSRVFormat;
- info.swizzleRTVFormat = swizzleInfo.mRTVFormat;
- }
- else
- {
- // The original texture format is suitable for swizzle operations
- info.swizzleTexFormat = texFormat;
- info.swizzleSRVFormat = srvFormat;
- info.swizzleRTVFormat = rtvFormat;
- }
- }
- else
- {
- // Not possible to swizzle with this texture format since it is either unsized or GL_NONE
- info.swizzleTexFormat = DXGI_FORMAT_UNKNOWN;
- info.swizzleSRVFormat = DXGI_FORMAT_UNKNOWN;
- info.swizzleRTVFormat = DXGI_FORMAT_UNKNOWN;
- }
-
- // Check if there is an initialization function for this texture format
- info.dataInitializerFunction = GetInternalFormatInitializer(internalFormat, texFormat);
- // Gather all the load functions for this internal format
- info.loadFunctions = GetLoadFunctionsMap(internalFormat, texFormat);
-
- ASSERT(info.loadFunctions.size() != 0 || internalFormat == GL_NONE);
-
- return info;
-}
-
-} // namespace
-
-TextureFormat::TextureFormat()
- : texFormat(DXGI_FORMAT_UNKNOWN),
- srvFormat(DXGI_FORMAT_UNKNOWN),
- rtvFormat(DXGI_FORMAT_UNKNOWN),
- dsvFormat(DXGI_FORMAT_UNKNOWN),
- renderFormat(DXGI_FORMAT_UNKNOWN),
- swizzleTexFormat(DXGI_FORMAT_UNKNOWN),
- swizzleSRVFormat(DXGI_FORMAT_UNKNOWN),
- swizzleRTVFormat(DXGI_FORMAT_UNKNOWN),
- dataInitializerFunction(NULL),
- loadFunctions()
-{
-}
-
-const TextureFormat &GetTextureFormatInfo(GLenum internalFormat,
- const Renderer11DeviceCaps &renderer11DeviceCaps)
+// static
+const Format &Format::Get(GLenum internalFormat, const Renderer11DeviceCaps &deviceCaps)
{
// clang-format off
switch (internalFormat)
{
- case GL_ALPHA:
- {
- if (OnlyFL10Plus(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_A8_UNORM,
- DXGI_FORMAT_A8_UNORM,
- DXGI_FORMAT_A8_UNORM,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else if (OnlyFL9_3(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
- }
case GL_ALPHA16F_EXT:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R16G16B16A16_FLOAT,
- DXGI_FORMAT_R16G16B16A16_FLOAT,
- DXGI_FORMAT_R16G16B16A16_FLOAT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_ALPHA16F_EXT,
+ angle::Format::ID::R16G16B16A16_FLOAT,
+ DXGI_FORMAT_R16G16B16A16_FLOAT,
+ DXGI_FORMAT_R16G16B16A16_FLOAT,
+ DXGI_FORMAT_R16G16B16A16_FLOAT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R16G16B16A16_FLOAT,
+ GL_RGBA16F,
+ nullptr);
+ return info;
}
case GL_ALPHA32F_EXT:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R32G32B32A32_FLOAT,
- DXGI_FORMAT_R32G32B32A32_FLOAT,
- DXGI_FORMAT_R32G32B32A32_FLOAT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_ALPHA32F_EXT,
+ angle::Format::ID::R32G32B32A32_FLOAT,
+ DXGI_FORMAT_R32G32B32A32_FLOAT,
+ DXGI_FORMAT_R32G32B32A32_FLOAT,
+ DXGI_FORMAT_R32G32B32A32_FLOAT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R32G32B32A32_FLOAT,
+ GL_RGBA32F,
+ nullptr);
+ return info;
}
case GL_ALPHA8_EXT:
{
- if (OnlyFL10Plus(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_A8_UNORM,
- DXGI_FORMAT_A8_UNORM,
- DXGI_FORMAT_A8_UNORM,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else if (OnlyFL9_3(renderer11DeviceCaps))
+ if (OnlyFL10Plus(deviceCaps))
{
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
+ static constexpr Format info(GL_ALPHA8_EXT,
+ angle::Format::ID::A8_UNORM,
+ DXGI_FORMAT_A8_UNORM,
+ DXGI_FORMAT_A8_UNORM,
+ DXGI_FORMAT_A8_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_A8_UNORM,
+ GL_RGBA8,
+ nullptr);
+ return info;
}
else
{
- break;
+ static constexpr Format info(GL_ALPHA8_EXT,
+ angle::Format::ID::R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ GL_RGBA8,
+ nullptr);
+ return info;
}
}
- case GL_BGR5_A1_ANGLEX:
+ case GL_BGR565_ANGLEX:
{
- if (AnyDevice(renderer11DeviceCaps))
+ if (SupportsFormat(DXGI_FORMAT_B5G6R5_UNORM, deviceCaps))
{
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_B8G8R8A8_UNORM,
- DXGI_FORMAT_B8G8R8A8_UNORM,
- DXGI_FORMAT_B8G8R8A8_UNORM,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
+ static constexpr Format info(GL_BGR565_ANGLEX,
+ angle::Format::ID::B5G6R5_UNORM,
+ DXGI_FORMAT_B5G6R5_UNORM,
+ DXGI_FORMAT_B5G6R5_UNORM,
+ DXGI_FORMAT_B5G6R5_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_B5G6R5_UNORM,
+ GL_RGBA8,
+ nullptr);
+ return info;
}
else
{
- break;
+ static constexpr Format info(GL_BGR565_ANGLEX,
+ angle::Format::ID::R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ GL_RGBA8,
+ nullptr);
+ return info;
}
}
- case GL_BGRA4_ANGLEX:
+ case GL_BGR5_A1_ANGLEX:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_B8G8R8A8_UNORM,
- DXGI_FORMAT_B8G8R8A8_UNORM,
- DXGI_FORMAT_B8G8R8A8_UNORM,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_BGR5_A1_ANGLEX,
+ angle::Format::ID::B8G8R8A8_UNORM,
+ DXGI_FORMAT_B8G8R8A8_UNORM,
+ DXGI_FORMAT_B8G8R8A8_UNORM,
+ DXGI_FORMAT_B8G8R8A8_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_B8G8R8A8_UNORM,
+ GL_BGRA8_EXT,
+ nullptr);
+ return info;
}
- case GL_BGRA8_EXT:
+ case GL_BGRA4_ANGLEX:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_B8G8R8A8_UNORM,
- DXGI_FORMAT_B8G8R8A8_UNORM,
- DXGI_FORMAT_B8G8R8A8_UNORM,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_BGRA4_ANGLEX,
+ angle::Format::ID::B8G8R8A8_UNORM,
+ DXGI_FORMAT_B8G8R8A8_UNORM,
+ DXGI_FORMAT_B8G8R8A8_UNORM,
+ DXGI_FORMAT_B8G8R8A8_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_B8G8R8A8_UNORM,
+ GL_BGRA8_EXT,
+ nullptr);
+ return info;
}
- case GL_BGRA_EXT:
+ case GL_BGRA8_EXT:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_B8G8R8A8_UNORM,
- DXGI_FORMAT_B8G8R8A8_UNORM,
- DXGI_FORMAT_B8G8R8A8_UNORM,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_BGRA8_EXT,
+ angle::Format::ID::B8G8R8A8_UNORM,
+ DXGI_FORMAT_B8G8R8A8_UNORM,
+ DXGI_FORMAT_B8G8R8A8_UNORM,
+ DXGI_FORMAT_B8G8R8A8_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_B8G8R8A8_UNORM,
+ GL_BGRA8_EXT,
+ nullptr);
+ return info;
+ }
+ case GL_BGRA8_SRGB_ANGLEX:
+ {
+ static constexpr Format info(GL_BGRA8_SRGB_ANGLEX,
+ angle::Format::ID::B8G8R8A8_UNORM_SRGB,
+ DXGI_FORMAT_B8G8R8A8_UNORM_SRGB,
+ DXGI_FORMAT_B8G8R8A8_UNORM_SRGB,
+ DXGI_FORMAT_B8G8R8A8_UNORM_SRGB,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_B8G8R8A8_UNORM_SRGB,
+ GL_BGRA8_SRGB_ANGLEX,
+ nullptr);
+ return info;
}
case GL_COMPRESSED_R11_EAC:
{
- if (OnlyFL10Plus(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8_UNORM,
- DXGI_FORMAT_R8_UNORM,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_COMPRESSED_R11_EAC,
+ angle::Format::ID::R8_UNORM,
+ DXGI_FORMAT_R8_UNORM,
+ DXGI_FORMAT_R8_UNORM,
+ DXGI_FORMAT_R8_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8_UNORM,
+ GL_RGBA8,
+ nullptr);
+ return info;
}
case GL_COMPRESSED_RG11_EAC:
{
- if (OnlyFL10Plus(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8_UNORM,
- DXGI_FORMAT_R8G8_UNORM,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_COMPRESSED_RG11_EAC,
+ angle::Format::ID::R8G8_UNORM,
+ DXGI_FORMAT_R8G8_UNORM,
+ DXGI_FORMAT_R8G8_UNORM,
+ DXGI_FORMAT_R8G8_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8_UNORM,
+ GL_RGBA8,
+ nullptr);
+ return info;
}
case GL_COMPRESSED_RGB8_ETC2:
{
- if (OnlyFL10Plus(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_COMPRESSED_RGB8_ETC2,
+ angle::Format::ID::R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ GL_RGBA8,
+ Initialize4ComponentData<GLubyte, 0x00, 0x00, 0x00, 0xFF>);
+ return info;
+ }
+ case GL_COMPRESSED_RGB8_LOSSY_DECODE_ETC2_ANGLE:
+ {
+ static constexpr Format info(GL_COMPRESSED_RGB8_LOSSY_DECODE_ETC2_ANGLE,
+ angle::Format::ID::BC1_RGB_UNORM_BLOCK,
+ DXGI_FORMAT_BC1_UNORM,
+ DXGI_FORMAT_BC1_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_BC1_UNORM,
+ GL_RGBA8,
+ nullptr);
+ return info;
}
case GL_COMPRESSED_RGB8_PUNCHTHROUGH_ALPHA1_ETC2:
{
- if (OnlyFL10Plus(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_COMPRESSED_RGB8_PUNCHTHROUGH_ALPHA1_ETC2,
+ angle::Format::ID::R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ GL_RGBA8,
+ Initialize4ComponentData<GLubyte, 0x00, 0x00, 0x00, 0xFF>);
+ return info;
+ }
+ case GL_COMPRESSED_RGB8_PUNCHTHROUGH_ALPHA1_LOSSY_DECODE_ETC2_ANGLE:
+ {
+ static constexpr Format info(GL_COMPRESSED_RGB8_PUNCHTHROUGH_ALPHA1_LOSSY_DECODE_ETC2_ANGLE,
+ angle::Format::ID::BC1_RGBA_UNORM_BLOCK,
+ DXGI_FORMAT_BC1_UNORM,
+ DXGI_FORMAT_BC1_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_BC1_UNORM,
+ GL_RGBA8,
+ nullptr);
+ return info;
}
case GL_COMPRESSED_RGBA8_ETC2_EAC:
{
- if (OnlyFL10Plus(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_COMPRESSED_RGBA8_ETC2_EAC,
+ angle::Format::ID::R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ GL_RGBA8,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_RGBA_ASTC_10x10_KHR:
+ {
+ static constexpr Format info(GL_COMPRESSED_RGBA_ASTC_10x10_KHR,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_RGBA_ASTC_10x5_KHR:
+ {
+ static constexpr Format info(GL_COMPRESSED_RGBA_ASTC_10x5_KHR,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_RGBA_ASTC_10x6_KHR:
+ {
+ static constexpr Format info(GL_COMPRESSED_RGBA_ASTC_10x6_KHR,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_RGBA_ASTC_10x8_KHR:
+ {
+ static constexpr Format info(GL_COMPRESSED_RGBA_ASTC_10x8_KHR,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_RGBA_ASTC_12x10_KHR:
+ {
+ static constexpr Format info(GL_COMPRESSED_RGBA_ASTC_12x10_KHR,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_RGBA_ASTC_12x12_KHR:
+ {
+ static constexpr Format info(GL_COMPRESSED_RGBA_ASTC_12x12_KHR,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_RGBA_ASTC_4x4_KHR:
+ {
+ static constexpr Format info(GL_COMPRESSED_RGBA_ASTC_4x4_KHR,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_RGBA_ASTC_5x4_KHR:
+ {
+ static constexpr Format info(GL_COMPRESSED_RGBA_ASTC_5x4_KHR,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_RGBA_ASTC_5x5_KHR:
+ {
+ static constexpr Format info(GL_COMPRESSED_RGBA_ASTC_5x5_KHR,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_RGBA_ASTC_6x5_KHR:
+ {
+ static constexpr Format info(GL_COMPRESSED_RGBA_ASTC_6x5_KHR,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_RGBA_ASTC_6x6_KHR:
+ {
+ static constexpr Format info(GL_COMPRESSED_RGBA_ASTC_6x6_KHR,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_RGBA_ASTC_8x5_KHR:
+ {
+ static constexpr Format info(GL_COMPRESSED_RGBA_ASTC_8x5_KHR,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_RGBA_ASTC_8x6_KHR:
+ {
+ static constexpr Format info(GL_COMPRESSED_RGBA_ASTC_8x6_KHR,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_RGBA_ASTC_8x8_KHR:
+ {
+ static constexpr Format info(GL_COMPRESSED_RGBA_ASTC_8x8_KHR,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
}
case GL_COMPRESSED_RGBA_S3TC_DXT1_EXT:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_BC1_UNORM,
- DXGI_FORMAT_BC1_UNORM,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_COMPRESSED_RGBA_S3TC_DXT1_EXT,
+ angle::Format::ID::BC1_RGBA_UNORM_BLOCK,
+ DXGI_FORMAT_BC1_UNORM,
+ DXGI_FORMAT_BC1_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_BC1_UNORM,
+ GL_RGBA8,
+ nullptr);
+ return info;
}
case GL_COMPRESSED_RGBA_S3TC_DXT3_ANGLE:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_BC2_UNORM,
- DXGI_FORMAT_BC2_UNORM,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_COMPRESSED_RGBA_S3TC_DXT3_ANGLE,
+ angle::Format::ID::BC2_RGBA_UNORM_BLOCK,
+ DXGI_FORMAT_BC2_UNORM,
+ DXGI_FORMAT_BC2_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_BC2_UNORM,
+ GL_RGBA8,
+ nullptr);
+ return info;
}
case GL_COMPRESSED_RGBA_S3TC_DXT5_ANGLE:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_BC3_UNORM,
- DXGI_FORMAT_BC3_UNORM,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_COMPRESSED_RGBA_S3TC_DXT5_ANGLE,
+ angle::Format::ID::BC3_RGBA_UNORM_BLOCK,
+ DXGI_FORMAT_BC3_UNORM,
+ DXGI_FORMAT_BC3_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_BC3_UNORM,
+ GL_RGBA8,
+ nullptr);
+ return info;
}
case GL_COMPRESSED_RGB_S3TC_DXT1_EXT:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_BC1_UNORM,
- DXGI_FORMAT_BC1_UNORM,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_COMPRESSED_RGB_S3TC_DXT1_EXT,
+ angle::Format::ID::BC1_RGB_UNORM_BLOCK,
+ DXGI_FORMAT_BC1_UNORM,
+ DXGI_FORMAT_BC1_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_BC1_UNORM,
+ GL_RGBA8,
+ nullptr);
+ return info;
}
case GL_COMPRESSED_SIGNED_R11_EAC:
{
- if (OnlyFL10Plus(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8_SNORM,
- DXGI_FORMAT_R8_SNORM,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_COMPRESSED_SIGNED_R11_EAC,
+ angle::Format::ID::R8_SNORM,
+ DXGI_FORMAT_R8_SNORM,
+ DXGI_FORMAT_R8_SNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8_SNORM,
+ GL_RGBA8_SNORM,
+ nullptr);
+ return info;
}
case GL_COMPRESSED_SIGNED_RG11_EAC:
{
- if (OnlyFL10Plus(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8_SNORM,
- DXGI_FORMAT_R8G8_SNORM,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_COMPRESSED_SIGNED_RG11_EAC,
+ angle::Format::ID::R8G8_SNORM,
+ DXGI_FORMAT_R8G8_SNORM,
+ DXGI_FORMAT_R8G8_SNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8_SNORM,
+ GL_RGBA8_SNORM,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_SRGB8_ALPHA8_ASTC_10x10_KHR:
+ {
+ static constexpr Format info(GL_COMPRESSED_SRGB8_ALPHA8_ASTC_10x10_KHR,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_SRGB8_ALPHA8_ASTC_10x5_KHR:
+ {
+ static constexpr Format info(GL_COMPRESSED_SRGB8_ALPHA8_ASTC_10x5_KHR,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_SRGB8_ALPHA8_ASTC_10x6_KHR:
+ {
+ static constexpr Format info(GL_COMPRESSED_SRGB8_ALPHA8_ASTC_10x6_KHR,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_SRGB8_ALPHA8_ASTC_10x8_KHR:
+ {
+ static constexpr Format info(GL_COMPRESSED_SRGB8_ALPHA8_ASTC_10x8_KHR,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_SRGB8_ALPHA8_ASTC_12x10_KHR:
+ {
+ static constexpr Format info(GL_COMPRESSED_SRGB8_ALPHA8_ASTC_12x10_KHR,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_SRGB8_ALPHA8_ASTC_12x12_KHR:
+ {
+ static constexpr Format info(GL_COMPRESSED_SRGB8_ALPHA8_ASTC_12x12_KHR,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_SRGB8_ALPHA8_ASTC_4x4_KHR:
+ {
+ static constexpr Format info(GL_COMPRESSED_SRGB8_ALPHA8_ASTC_4x4_KHR,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_SRGB8_ALPHA8_ASTC_5x4_KHR:
+ {
+ static constexpr Format info(GL_COMPRESSED_SRGB8_ALPHA8_ASTC_5x4_KHR,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_SRGB8_ALPHA8_ASTC_5x5_KHR:
+ {
+ static constexpr Format info(GL_COMPRESSED_SRGB8_ALPHA8_ASTC_5x5_KHR,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_SRGB8_ALPHA8_ASTC_6x5_KHR:
+ {
+ static constexpr Format info(GL_COMPRESSED_SRGB8_ALPHA8_ASTC_6x5_KHR,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_SRGB8_ALPHA8_ASTC_6x6_KHR:
+ {
+ static constexpr Format info(GL_COMPRESSED_SRGB8_ALPHA8_ASTC_6x6_KHR,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_SRGB8_ALPHA8_ASTC_8x5_KHR:
+ {
+ static constexpr Format info(GL_COMPRESSED_SRGB8_ALPHA8_ASTC_8x5_KHR,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_SRGB8_ALPHA8_ASTC_8x6_KHR:
+ {
+ static constexpr Format info(GL_COMPRESSED_SRGB8_ALPHA8_ASTC_8x6_KHR,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_SRGB8_ALPHA8_ASTC_8x8_KHR:
+ {
+ static constexpr Format info(GL_COMPRESSED_SRGB8_ALPHA8_ASTC_8x8_KHR,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
}
case GL_COMPRESSED_SRGB8_ALPHA8_ETC2_EAC:
{
- if (OnlyFL10Plus(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
- DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_COMPRESSED_SRGB8_ALPHA8_ETC2_EAC,
+ angle::Format::ID::R8G8B8A8_UNORM_SRGB,
+ DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
+ DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
+ DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
+ GL_SRGB8_ALPHA8,
+ nullptr);
+ return info;
}
case GL_COMPRESSED_SRGB8_ETC2:
{
- if (OnlyFL10Plus(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
- DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_COMPRESSED_SRGB8_ETC2,
+ angle::Format::ID::R8G8B8A8_UNORM_SRGB,
+ DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
+ DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
+ DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
+ GL_SRGB8_ALPHA8,
+ Initialize4ComponentData<GLubyte, 0x00, 0x00, 0x00, 0xFF>);
+ return info;
+ }
+ case GL_COMPRESSED_SRGB8_LOSSY_DECODE_ETC2_ANGLE:
+ {
+ static constexpr Format info(GL_COMPRESSED_SRGB8_LOSSY_DECODE_ETC2_ANGLE,
+ angle::Format::ID::BC1_RGB_UNORM_SRGB_BLOCK,
+ DXGI_FORMAT_BC1_UNORM_SRGB,
+ DXGI_FORMAT_BC1_UNORM_SRGB,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_BC1_UNORM_SRGB,
+ GL_RGBA8,
+ nullptr);
+ return info;
}
case GL_COMPRESSED_SRGB8_PUNCHTHROUGH_ALPHA1_ETC2:
{
- if (OnlyFL10Plus(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
- DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_COMPRESSED_SRGB8_PUNCHTHROUGH_ALPHA1_ETC2,
+ angle::Format::ID::R8G8B8A8_UNORM_SRGB,
+ DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
+ DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
+ DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
+ GL_SRGB8_ALPHA8,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_SRGB8_PUNCHTHROUGH_ALPHA1_LOSSY_DECODE_ETC2_ANGLE:
+ {
+ static constexpr Format info(GL_COMPRESSED_SRGB8_PUNCHTHROUGH_ALPHA1_LOSSY_DECODE_ETC2_ANGLE,
+ angle::Format::ID::BC1_RGBA_UNORM_SRGB_BLOCK,
+ DXGI_FORMAT_BC1_UNORM_SRGB,
+ DXGI_FORMAT_BC1_UNORM_SRGB,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_BC1_UNORM_SRGB,
+ GL_RGBA8,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_SRGB_ALPHA_S3TC_DXT1_EXT:
+ {
+ static constexpr Format info(GL_COMPRESSED_SRGB_ALPHA_S3TC_DXT1_EXT,
+ angle::Format::ID::BC1_RGBA_UNORM_SRGB_BLOCK,
+ DXGI_FORMAT_BC1_UNORM_SRGB,
+ DXGI_FORMAT_BC1_UNORM_SRGB,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_BC1_UNORM_SRGB,
+ GL_RGBA8,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_SRGB_ALPHA_S3TC_DXT3_EXT:
+ {
+ static constexpr Format info(GL_COMPRESSED_SRGB_ALPHA_S3TC_DXT3_EXT,
+ angle::Format::ID::BC2_RGBA_UNORM_SRGB_BLOCK,
+ DXGI_FORMAT_BC2_UNORM_SRGB,
+ DXGI_FORMAT_BC2_UNORM_SRGB,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_BC2_UNORM_SRGB,
+ GL_RGBA8,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_SRGB_ALPHA_S3TC_DXT5_EXT:
+ {
+ static constexpr Format info(GL_COMPRESSED_SRGB_ALPHA_S3TC_DXT5_EXT,
+ angle::Format::ID::BC3_RGBA_UNORM_SRGB_BLOCK,
+ DXGI_FORMAT_BC3_UNORM_SRGB,
+ DXGI_FORMAT_BC3_UNORM_SRGB,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_BC3_UNORM_SRGB,
+ GL_RGBA8,
+ nullptr);
+ return info;
+ }
+ case GL_COMPRESSED_SRGB_S3TC_DXT1_EXT:
+ {
+ static constexpr Format info(GL_COMPRESSED_SRGB_S3TC_DXT1_EXT,
+ angle::Format::ID::BC1_RGB_UNORM_SRGB_BLOCK,
+ DXGI_FORMAT_BC1_UNORM_SRGB,
+ DXGI_FORMAT_BC1_UNORM_SRGB,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_BC1_UNORM_SRGB,
+ GL_RGBA8,
+ nullptr);
+ return info;
}
case GL_DEPTH24_STENCIL8:
{
- if (OnlyFL9_3(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_D24_UNORM_S8_UINT,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_D24_UNORM_S8_UINT);
- return textureFormat;
- }
- else if (OnlyFL10Plus(renderer11DeviceCaps))
+ if (OnlyFL10Plus(deviceCaps))
{
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R24G8_TYPELESS,
- DXGI_FORMAT_R24_UNORM_X8_TYPELESS,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_D24_UNORM_S8_UINT);
- return textureFormat;
+ static constexpr Format info(GL_DEPTH24_STENCIL8,
+ angle::Format::ID::D24_UNORM_S8_UINT,
+ DXGI_FORMAT_R24G8_TYPELESS,
+ DXGI_FORMAT_R24_UNORM_X8_TYPELESS,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_D24_UNORM_S8_UINT,
+ DXGI_FORMAT_R24_UNORM_X8_TYPELESS,
+ GL_RGBA32F,
+ nullptr);
+ return info;
}
else
{
- break;
+ static constexpr Format info(GL_DEPTH24_STENCIL8,
+ angle::Format::ID::D24_UNORM_S8_UINT,
+ DXGI_FORMAT_D24_UNORM_S8_UINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_D24_UNORM_S8_UINT,
+ DXGI_FORMAT_UNKNOWN,
+ GL_RGBA32F,
+ nullptr);
+ return info;
}
}
case GL_DEPTH32F_STENCIL8:
{
- if (OnlyFL9_3(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else if (OnlyFL10Plus(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R32G8X24_TYPELESS,
- DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_D32_FLOAT_S8X24_UINT);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_DEPTH32F_STENCIL8,
+ angle::Format::ID::D32_FLOAT_S8X24_UINT,
+ DXGI_FORMAT_R32G8X24_TYPELESS,
+ DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_D32_FLOAT_S8X24_UINT,
+ DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS,
+ GL_RGBA32F,
+ nullptr);
+ return info;
}
case GL_DEPTH_COMPONENT16:
{
- if (OnlyFL9_3(renderer11DeviceCaps))
+ if (OnlyFL10Plus(deviceCaps))
{
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_D16_UNORM,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_D16_UNORM);
- return textureFormat;
- }
- else if (OnlyFL10Plus(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R16_TYPELESS,
- DXGI_FORMAT_R16_UNORM,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_D16_UNORM);
- return textureFormat;
+ static constexpr Format info(GL_DEPTH_COMPONENT16,
+ angle::Format::ID::D16_UNORM,
+ DXGI_FORMAT_R16_TYPELESS,
+ DXGI_FORMAT_R16_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_D16_UNORM,
+ DXGI_FORMAT_R16_UNORM,
+ GL_RGBA16_EXT,
+ nullptr);
+ return info;
}
else
{
- break;
+ static constexpr Format info(GL_DEPTH_COMPONENT16,
+ angle::Format::ID::D16_UNORM,
+ DXGI_FORMAT_D16_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_D16_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ GL_RGBA16_EXT,
+ nullptr);
+ return info;
}
}
case GL_DEPTH_COMPONENT24:
{
- if (OnlyFL9_3(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_D24_UNORM_S8_UINT,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_D24_UNORM_S8_UINT);
- return textureFormat;
- }
- else if (OnlyFL10Plus(renderer11DeviceCaps))
+ if (OnlyFL10Plus(deviceCaps))
{
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R24G8_TYPELESS,
- DXGI_FORMAT_R24_UNORM_X8_TYPELESS,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_D24_UNORM_S8_UINT);
- return textureFormat;
+ static constexpr Format info(GL_DEPTH_COMPONENT24,
+ angle::Format::ID::D24_UNORM_S8_UINT,
+ DXGI_FORMAT_R24G8_TYPELESS,
+ DXGI_FORMAT_R24_UNORM_X8_TYPELESS,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_D24_UNORM_S8_UINT,
+ DXGI_FORMAT_R24_UNORM_X8_TYPELESS,
+ GL_RGBA32F,
+ nullptr);
+ return info;
}
else
{
- break;
+ static constexpr Format info(GL_DEPTH_COMPONENT24,
+ angle::Format::ID::D24_UNORM_S8_UINT,
+ DXGI_FORMAT_D24_UNORM_S8_UINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_D24_UNORM_S8_UINT,
+ DXGI_FORMAT_UNKNOWN,
+ GL_RGBA32F,
+ nullptr);
+ return info;
}
}
case GL_DEPTH_COMPONENT32F:
{
- if (OnlyFL9_3(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else if (OnlyFL10Plus(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R32_TYPELESS,
- DXGI_FORMAT_R32_FLOAT,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_D32_FLOAT);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_DEPTH_COMPONENT32F,
+ angle::Format::ID::D32_FLOAT,
+ DXGI_FORMAT_R32_TYPELESS,
+ DXGI_FORMAT_R32_FLOAT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_D32_FLOAT,
+ DXGI_FORMAT_R32_FLOAT,
+ GL_RGBA32F,
+ nullptr);
+ return info;
}
case GL_DEPTH_COMPONENT32_OES:
{
- if (OnlyFL10Plus(renderer11DeviceCaps))
+ if (OnlyFL10Plus(deviceCaps))
{
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R24G8_TYPELESS,
- DXGI_FORMAT_R24_UNORM_X8_TYPELESS,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_D24_UNORM_S8_UINT);
- return textureFormat;
+ static constexpr Format info(GL_DEPTH_COMPONENT32_OES,
+ angle::Format::ID::D24_UNORM_S8_UINT,
+ DXGI_FORMAT_R24G8_TYPELESS,
+ DXGI_FORMAT_R24_UNORM_X8_TYPELESS,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_D24_UNORM_S8_UINT,
+ DXGI_FORMAT_R24_UNORM_X8_TYPELESS,
+ GL_RGBA32F,
+ nullptr);
+ return info;
}
else
{
- break;
+ static constexpr Format info(GL_DEPTH_COMPONENT32_OES,
+ angle::Format::ID::D24_UNORM_S8_UINT,
+ DXGI_FORMAT_D24_UNORM_S8_UINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_D24_UNORM_S8_UINT,
+ DXGI_FORMAT_UNKNOWN,
+ GL_RGBA32F,
+ nullptr);
+ return info;
}
}
case GL_ETC1_RGB8_LOSSY_DECODE_ANGLE:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_BC1_UNORM,
- DXGI_FORMAT_BC1_UNORM,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_ETC1_RGB8_LOSSY_DECODE_ANGLE,
+ angle::Format::ID::BC1_RGB_UNORM_BLOCK,
+ DXGI_FORMAT_BC1_UNORM,
+ DXGI_FORMAT_BC1_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_BC1_UNORM,
+ GL_RGBA8,
+ nullptr);
+ return info;
}
case GL_ETC1_RGB8_OES:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
- }
- case GL_LUMINANCE:
- {
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_ETC1_RGB8_OES,
+ angle::Format::ID::R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ GL_RGBA8,
+ Initialize4ComponentData<GLubyte, 0x00, 0x00, 0x00, 0xFF>);
+ return info;
}
case GL_LUMINANCE16F_EXT:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R16G16B16A16_FLOAT,
- DXGI_FORMAT_R16G16B16A16_FLOAT,
- DXGI_FORMAT_R16G16B16A16_FLOAT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_LUMINANCE16F_EXT,
+ angle::Format::ID::R16G16B16A16_FLOAT,
+ DXGI_FORMAT_R16G16B16A16_FLOAT,
+ DXGI_FORMAT_R16G16B16A16_FLOAT,
+ DXGI_FORMAT_R16G16B16A16_FLOAT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R16G16B16A16_FLOAT,
+ GL_RGBA16F,
+ Initialize4ComponentData<GLhalf, 0x0000, 0x0000, 0x0000, gl::Float16One>);
+ return info;
}
case GL_LUMINANCE32F_EXT:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R32G32B32A32_FLOAT,
- DXGI_FORMAT_R32G32B32A32_FLOAT,
- DXGI_FORMAT_R32G32B32A32_FLOAT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_LUMINANCE32F_EXT,
+ angle::Format::ID::R32G32B32A32_FLOAT,
+ DXGI_FORMAT_R32G32B32A32_FLOAT,
+ DXGI_FORMAT_R32G32B32A32_FLOAT,
+ DXGI_FORMAT_R32G32B32A32_FLOAT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R32G32B32A32_FLOAT,
+ GL_RGBA32F,
+ Initialize4ComponentData<GLfloat, 0x00000000, 0x00000000, 0x00000000, gl::Float32One>);
+ return info;
}
case GL_LUMINANCE8_ALPHA8_EXT:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_LUMINANCE8_ALPHA8_EXT,
+ angle::Format::ID::R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ GL_RGBA8,
+ nullptr);
+ return info;
}
case GL_LUMINANCE8_EXT:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
- }
- case GL_LUMINANCE_ALPHA:
- {
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_LUMINANCE8_EXT,
+ angle::Format::ID::R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ GL_RGBA8,
+ Initialize4ComponentData<GLubyte, 0x00, 0x00, 0x00, 0xFF>);
+ return info;
}
case GL_LUMINANCE_ALPHA16F_EXT:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R16G16B16A16_FLOAT,
- DXGI_FORMAT_R16G16B16A16_FLOAT,
- DXGI_FORMAT_R16G16B16A16_FLOAT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_LUMINANCE_ALPHA16F_EXT,
+ angle::Format::ID::R16G16B16A16_FLOAT,
+ DXGI_FORMAT_R16G16B16A16_FLOAT,
+ DXGI_FORMAT_R16G16B16A16_FLOAT,
+ DXGI_FORMAT_R16G16B16A16_FLOAT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R16G16B16A16_FLOAT,
+ GL_RGBA16F,
+ nullptr);
+ return info;
}
case GL_LUMINANCE_ALPHA32F_EXT:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R32G32B32A32_FLOAT,
- DXGI_FORMAT_R32G32B32A32_FLOAT,
- DXGI_FORMAT_R32G32B32A32_FLOAT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_LUMINANCE_ALPHA32F_EXT,
+ angle::Format::ID::R32G32B32A32_FLOAT,
+ DXGI_FORMAT_R32G32B32A32_FLOAT,
+ DXGI_FORMAT_R32G32B32A32_FLOAT,
+ DXGI_FORMAT_R32G32B32A32_FLOAT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R32G32B32A32_FLOAT,
+ GL_RGBA32F,
+ nullptr);
+ return info;
}
case GL_NONE:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_NONE,
+ angle::Format::ID::NONE,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ GL_NONE,
+ nullptr);
+ return info;
}
case GL_R11F_G11F_B10F:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R11G11B10_FLOAT,
- DXGI_FORMAT_R11G11B10_FLOAT,
- DXGI_FORMAT_R11G11B10_FLOAT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_R11F_G11F_B10F,
+ angle::Format::ID::R11G11B10_FLOAT,
+ DXGI_FORMAT_R11G11B10_FLOAT,
+ DXGI_FORMAT_R11G11B10_FLOAT,
+ DXGI_FORMAT_R11G11B10_FLOAT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R11G11B10_FLOAT,
+ GL_RGBA16F_EXT,
+ nullptr);
+ return info;
}
case GL_R16F:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R16_FLOAT,
- DXGI_FORMAT_R16_FLOAT,
- DXGI_FORMAT_R16_FLOAT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_R16F,
+ angle::Format::ID::R16_FLOAT,
+ DXGI_FORMAT_R16_FLOAT,
+ DXGI_FORMAT_R16_FLOAT,
+ DXGI_FORMAT_R16_FLOAT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R16_FLOAT,
+ GL_RGBA16F_EXT,
+ nullptr);
+ return info;
}
case GL_R16I:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R16_SINT,
- DXGI_FORMAT_R16_SINT,
- DXGI_FORMAT_R16_SINT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_R16I,
+ angle::Format::ID::R16_SINT,
+ DXGI_FORMAT_R16_SINT,
+ DXGI_FORMAT_R16_SINT,
+ DXGI_FORMAT_R16_SINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R16_SINT,
+ GL_RGBA16I,
+ nullptr);
+ return info;
}
case GL_R16UI:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R16_UINT,
- DXGI_FORMAT_R16_UINT,
- DXGI_FORMAT_R16_UINT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_R16UI,
+ angle::Format::ID::R16_UINT,
+ DXGI_FORMAT_R16_UINT,
+ DXGI_FORMAT_R16_UINT,
+ DXGI_FORMAT_R16_UINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R16_UINT,
+ GL_RGBA16I,
+ nullptr);
+ return info;
+ }
+ case GL_R16_EXT:
+ {
+ static constexpr Format info(GL_R16_EXT,
+ angle::Format::ID::R16_UNORM,
+ DXGI_FORMAT_R16_UNORM,
+ DXGI_FORMAT_R16_UNORM,
+ DXGI_FORMAT_R16_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R16_UNORM,
+ GL_RGBA16_EXT,
+ nullptr);
+ return info;
+ }
+ case GL_R16_SNORM_EXT:
+ {
+ static constexpr Format info(GL_R16_SNORM_EXT,
+ angle::Format::ID::R16_SNORM,
+ DXGI_FORMAT_R16_SNORM,
+ DXGI_FORMAT_R16_SNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R16_SNORM,
+ GL_RGBA16_SNORM_EXT,
+ nullptr);
+ return info;
}
case GL_R32F:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R32_FLOAT,
- DXGI_FORMAT_R32_FLOAT,
- DXGI_FORMAT_R32_FLOAT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_R32F,
+ angle::Format::ID::R32_FLOAT,
+ DXGI_FORMAT_R32_FLOAT,
+ DXGI_FORMAT_R32_FLOAT,
+ DXGI_FORMAT_R32_FLOAT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R32_FLOAT,
+ GL_RGBA32F,
+ nullptr);
+ return info;
}
case GL_R32I:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R32_SINT,
- DXGI_FORMAT_R32_SINT,
- DXGI_FORMAT_R32_SINT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_R32I,
+ angle::Format::ID::R32_SINT,
+ DXGI_FORMAT_R32_SINT,
+ DXGI_FORMAT_R32_SINT,
+ DXGI_FORMAT_R32_SINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R32_SINT,
+ GL_RGBA32I,
+ nullptr);
+ return info;
}
case GL_R32UI:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R32_UINT,
- DXGI_FORMAT_R32_UINT,
- DXGI_FORMAT_R32_UINT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_R32UI,
+ angle::Format::ID::R32_UINT,
+ DXGI_FORMAT_R32_UINT,
+ DXGI_FORMAT_R32_UINT,
+ DXGI_FORMAT_R32_UINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R32_UINT,
+ GL_RGBA32I,
+ nullptr);
+ return info;
}
case GL_R8:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8_UNORM,
- DXGI_FORMAT_R8_UNORM,
- DXGI_FORMAT_R8_UNORM,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_R8,
+ angle::Format::ID::R8_UNORM,
+ DXGI_FORMAT_R8_UNORM,
+ DXGI_FORMAT_R8_UNORM,
+ DXGI_FORMAT_R8_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8_UNORM,
+ GL_RGBA8,
+ nullptr);
+ return info;
}
case GL_R8I:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8_SINT,
- DXGI_FORMAT_R8_SINT,
- DXGI_FORMAT_R8_SINT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_R8I,
+ angle::Format::ID::R8_SINT,
+ DXGI_FORMAT_R8_SINT,
+ DXGI_FORMAT_R8_SINT,
+ DXGI_FORMAT_R8_SINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8_SINT,
+ GL_RGBA8I,
+ nullptr);
+ return info;
}
case GL_R8UI:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8_UINT,
- DXGI_FORMAT_R8_UINT,
- DXGI_FORMAT_R8_UINT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_R8UI,
+ angle::Format::ID::R8_UINT,
+ DXGI_FORMAT_R8_UINT,
+ DXGI_FORMAT_R8_UINT,
+ DXGI_FORMAT_R8_UINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8_UINT,
+ GL_RGBA8I,
+ nullptr);
+ return info;
}
case GL_R8_SNORM:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8_SNORM,
- DXGI_FORMAT_R8_SNORM,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_R8_SNORM,
+ angle::Format::ID::R8_SNORM,
+ DXGI_FORMAT_R8_SNORM,
+ DXGI_FORMAT_R8_SNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8_SNORM,
+ GL_RGBA8_SNORM,
+ nullptr);
+ return info;
}
case GL_RG16F:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R16G16_FLOAT,
- DXGI_FORMAT_R16G16_FLOAT,
- DXGI_FORMAT_R16G16_FLOAT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RG16F,
+ angle::Format::ID::R16G16_FLOAT,
+ DXGI_FORMAT_R16G16_FLOAT,
+ DXGI_FORMAT_R16G16_FLOAT,
+ DXGI_FORMAT_R16G16_FLOAT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R16G16_FLOAT,
+ GL_RGBA16F_EXT,
+ nullptr);
+ return info;
}
case GL_RG16I:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R16G16_SINT,
- DXGI_FORMAT_R16G16_SINT,
- DXGI_FORMAT_R16G16_SINT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RG16I,
+ angle::Format::ID::R16G16_SINT,
+ DXGI_FORMAT_R16G16_SINT,
+ DXGI_FORMAT_R16G16_SINT,
+ DXGI_FORMAT_R16G16_SINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R16G16_SINT,
+ GL_RGBA16I,
+ nullptr);
+ return info;
}
case GL_RG16UI:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R16G16_UINT,
- DXGI_FORMAT_R16G16_UINT,
- DXGI_FORMAT_R16G16_UINT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RG16UI,
+ angle::Format::ID::R16G16_UINT,
+ DXGI_FORMAT_R16G16_UINT,
+ DXGI_FORMAT_R16G16_UINT,
+ DXGI_FORMAT_R16G16_UINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R16G16_UINT,
+ GL_RGBA16I,
+ nullptr);
+ return info;
+ }
+ case GL_RG16_EXT:
+ {
+ static constexpr Format info(GL_RG16_EXT,
+ angle::Format::ID::R16G16_UNORM,
+ DXGI_FORMAT_R16G16_UNORM,
+ DXGI_FORMAT_R16G16_UNORM,
+ DXGI_FORMAT_R16G16_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R16G16_UNORM,
+ GL_RGBA16_EXT,
+ nullptr);
+ return info;
+ }
+ case GL_RG16_SNORM_EXT:
+ {
+ static constexpr Format info(GL_RG16_SNORM_EXT,
+ angle::Format::ID::R16G16_SNORM,
+ DXGI_FORMAT_R16G16_SNORM,
+ DXGI_FORMAT_R16G16_SNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R16G16_SNORM,
+ GL_RGBA16_SNORM_EXT,
+ nullptr);
+ return info;
}
case GL_RG32F:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R32G32_FLOAT,
- DXGI_FORMAT_R32G32_FLOAT,
- DXGI_FORMAT_R32G32_FLOAT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RG32F,
+ angle::Format::ID::R32G32_FLOAT,
+ DXGI_FORMAT_R32G32_FLOAT,
+ DXGI_FORMAT_R32G32_FLOAT,
+ DXGI_FORMAT_R32G32_FLOAT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R32G32_FLOAT,
+ GL_RGBA32F,
+ nullptr);
+ return info;
}
case GL_RG32I:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R32G32_SINT,
- DXGI_FORMAT_R32G32_SINT,
- DXGI_FORMAT_R32G32_SINT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RG32I,
+ angle::Format::ID::R32G32_SINT,
+ DXGI_FORMAT_R32G32_SINT,
+ DXGI_FORMAT_R32G32_SINT,
+ DXGI_FORMAT_R32G32_SINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R32G32_SINT,
+ GL_RGBA32I,
+ nullptr);
+ return info;
}
case GL_RG32UI:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R32G32_UINT,
- DXGI_FORMAT_R32G32_UINT,
- DXGI_FORMAT_R32G32_UINT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RG32UI,
+ angle::Format::ID::R32G32_UINT,
+ DXGI_FORMAT_R32G32_UINT,
+ DXGI_FORMAT_R32G32_UINT,
+ DXGI_FORMAT_R32G32_UINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R32G32_UINT,
+ GL_RGBA32I,
+ nullptr);
+ return info;
}
case GL_RG8:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8_UNORM,
- DXGI_FORMAT_R8G8_UNORM,
- DXGI_FORMAT_R8G8_UNORM,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RG8,
+ angle::Format::ID::R8G8_UNORM,
+ DXGI_FORMAT_R8G8_UNORM,
+ DXGI_FORMAT_R8G8_UNORM,
+ DXGI_FORMAT_R8G8_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8_UNORM,
+ GL_RGBA8,
+ nullptr);
+ return info;
}
case GL_RG8I:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8_SINT,
- DXGI_FORMAT_R8G8_SINT,
- DXGI_FORMAT_R8G8_SINT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RG8I,
+ angle::Format::ID::R8G8_SINT,
+ DXGI_FORMAT_R8G8_SINT,
+ DXGI_FORMAT_R8G8_SINT,
+ DXGI_FORMAT_R8G8_SINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8_SINT,
+ GL_RGBA8I,
+ nullptr);
+ return info;
}
case GL_RG8UI:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8_UINT,
- DXGI_FORMAT_R8G8_UINT,
- DXGI_FORMAT_R8G8_UINT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RG8UI,
+ angle::Format::ID::R8G8_UINT,
+ DXGI_FORMAT_R8G8_UINT,
+ DXGI_FORMAT_R8G8_UINT,
+ DXGI_FORMAT_R8G8_UINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8_UINT,
+ GL_RGBA8I,
+ nullptr);
+ return info;
}
case GL_RG8_SNORM:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8_SNORM,
- DXGI_FORMAT_R8G8_SNORM,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RG8_SNORM,
+ angle::Format::ID::R8G8_SNORM,
+ DXGI_FORMAT_R8G8_SNORM,
+ DXGI_FORMAT_R8G8_SNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8_SNORM,
+ GL_RGBA8_SNORM,
+ nullptr);
+ return info;
}
case GL_RGB:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RGB,
+ angle::Format::ID::R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ GL_RGBA8,
+ Initialize4ComponentData<GLubyte, 0x00, 0x00, 0x00, 0xFF>);
+ return info;
}
case GL_RGB10_A2:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R10G10B10A2_UNORM,
- DXGI_FORMAT_R10G10B10A2_UNORM,
- DXGI_FORMAT_R10G10B10A2_UNORM,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RGB10_A2,
+ angle::Format::ID::R10G10B10A2_UNORM,
+ DXGI_FORMAT_R10G10B10A2_UNORM,
+ DXGI_FORMAT_R10G10B10A2_UNORM,
+ DXGI_FORMAT_R10G10B10A2_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R10G10B10A2_UNORM,
+ GL_RGBA16_EXT,
+ nullptr);
+ return info;
}
case GL_RGB10_A2UI:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R10G10B10A2_UINT,
- DXGI_FORMAT_R10G10B10A2_UINT,
- DXGI_FORMAT_R10G10B10A2_UINT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RGB10_A2UI,
+ angle::Format::ID::R10G10B10A2_UINT,
+ DXGI_FORMAT_R10G10B10A2_UINT,
+ DXGI_FORMAT_R10G10B10A2_UINT,
+ DXGI_FORMAT_R10G10B10A2_UINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R10G10B10A2_UINT,
+ GL_RGBA16I,
+ nullptr);
+ return info;
}
case GL_RGB16F:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R16G16B16A16_FLOAT,
- DXGI_FORMAT_R16G16B16A16_FLOAT,
- DXGI_FORMAT_R16G16B16A16_FLOAT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RGB16F,
+ angle::Format::ID::R16G16B16A16_FLOAT,
+ DXGI_FORMAT_R16G16B16A16_FLOAT,
+ DXGI_FORMAT_R16G16B16A16_FLOAT,
+ DXGI_FORMAT_R16G16B16A16_FLOAT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R16G16B16A16_FLOAT,
+ GL_RGBA16F,
+ Initialize4ComponentData<GLhalf, 0x0000, 0x0000, 0x0000, gl::Float16One>);
+ return info;
}
case GL_RGB16I:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R16G16B16A16_SINT,
- DXGI_FORMAT_R16G16B16A16_SINT,
- DXGI_FORMAT_R16G16B16A16_SINT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RGB16I,
+ angle::Format::ID::R16G16B16A16_SINT,
+ DXGI_FORMAT_R16G16B16A16_SINT,
+ DXGI_FORMAT_R16G16B16A16_SINT,
+ DXGI_FORMAT_R16G16B16A16_SINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R16G16B16A16_SINT,
+ GL_RGBA16I,
+ Initialize4ComponentData<GLshort, 0x0000, 0x0000, 0x0000, 0x0001>);
+ return info;
}
case GL_RGB16UI:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R16G16B16A16_UINT,
- DXGI_FORMAT_R16G16B16A16_UINT,
- DXGI_FORMAT_R16G16B16A16_UINT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RGB16UI,
+ angle::Format::ID::R16G16B16A16_UINT,
+ DXGI_FORMAT_R16G16B16A16_UINT,
+ DXGI_FORMAT_R16G16B16A16_UINT,
+ DXGI_FORMAT_R16G16B16A16_UINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R16G16B16A16_UINT,
+ GL_RGBA16UI,
+ Initialize4ComponentData<GLushort, 0x0000, 0x0000, 0x0000, 0x0001>);
+ return info;
+ }
+ case GL_RGB16_EXT:
+ {
+ static constexpr Format info(GL_RGB16_EXT,
+ angle::Format::ID::R16G16B16A16_UNORM,
+ DXGI_FORMAT_R16G16B16A16_UNORM,
+ DXGI_FORMAT_R16G16B16A16_UNORM,
+ DXGI_FORMAT_R16G16B16A16_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R16G16B16A16_UNORM,
+ GL_RGBA16_EXT,
+ Initialize4ComponentData<GLubyte, 0x0000, 0x0000, 0x0000, 0xFFFF>);
+ return info;
+ }
+ case GL_RGB16_SNORM_EXT:
+ {
+ static constexpr Format info(GL_RGB16_SNORM_EXT,
+ angle::Format::ID::R16G16B16A16_SNORM,
+ DXGI_FORMAT_R16G16B16A16_SNORM,
+ DXGI_FORMAT_R16G16B16A16_SNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R16G16B16A16_SNORM,
+ GL_RGBA16_SNORM_EXT,
+ Initialize4ComponentData<GLushort, 0x0000, 0x0000, 0x0000, 0x7FFF>);
+ return info;
}
case GL_RGB32F:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R32G32B32A32_FLOAT,
- DXGI_FORMAT_R32G32B32A32_FLOAT,
- DXGI_FORMAT_R32G32B32A32_FLOAT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RGB32F,
+ angle::Format::ID::R32G32B32A32_FLOAT,
+ DXGI_FORMAT_R32G32B32A32_FLOAT,
+ DXGI_FORMAT_R32G32B32A32_FLOAT,
+ DXGI_FORMAT_R32G32B32A32_FLOAT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R32G32B32A32_FLOAT,
+ GL_RGBA32F,
+ Initialize4ComponentData<GLfloat, 0x00000000, 0x00000000, 0x00000000, gl::Float32One>);
+ return info;
}
case GL_RGB32I:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R32G32B32A32_SINT,
- DXGI_FORMAT_R32G32B32A32_SINT,
- DXGI_FORMAT_R32G32B32A32_SINT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RGB32I,
+ angle::Format::ID::R32G32B32A32_SINT,
+ DXGI_FORMAT_R32G32B32A32_SINT,
+ DXGI_FORMAT_R32G32B32A32_SINT,
+ DXGI_FORMAT_R32G32B32A32_SINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R32G32B32A32_SINT,
+ GL_RGBA32I,
+ Initialize4ComponentData<GLint, 0x00000000, 0x00000000, 0x00000000, 0x00000001>);
+ return info;
}
case GL_RGB32UI:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R32G32B32A32_UINT,
- DXGI_FORMAT_R32G32B32A32_UINT,
- DXGI_FORMAT_R32G32B32A32_UINT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RGB32UI,
+ angle::Format::ID::R32G32B32A32_UINT,
+ DXGI_FORMAT_R32G32B32A32_UINT,
+ DXGI_FORMAT_R32G32B32A32_UINT,
+ DXGI_FORMAT_R32G32B32A32_UINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R32G32B32A32_UINT,
+ GL_RGBA32UI,
+ Initialize4ComponentData<GLuint, 0x00000000, 0x00000000, 0x00000000, 0x00000001>);
+ return info;
}
case GL_RGB565:
{
- if (SupportsFormat<DXGI_FORMAT_B5G6R5_UNORM,false>(renderer11DeviceCaps))
+ if (SupportsFormat(DXGI_FORMAT_B5G6R5_UNORM, deviceCaps))
{
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else if (SupportsFormat<DXGI_FORMAT_B5G6R5_UNORM,true>(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_B5G6R5_UNORM,
- DXGI_FORMAT_B5G6R5_UNORM,
- DXGI_FORMAT_B5G6R5_UNORM,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
+ static constexpr Format info(GL_RGB565,
+ angle::Format::ID::B5G6R5_UNORM,
+ DXGI_FORMAT_B5G6R5_UNORM,
+ DXGI_FORMAT_B5G6R5_UNORM,
+ DXGI_FORMAT_B5G6R5_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_B5G6R5_UNORM,
+ GL_RGBA8,
+ nullptr);
+ return info;
}
else
{
- break;
+ static constexpr Format info(GL_RGB565,
+ angle::Format::ID::R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ GL_RGBA8,
+ Initialize4ComponentData<GLubyte, 0x00, 0x00, 0x00, 0xFF>);
+ return info;
}
}
case GL_RGB5_A1:
{
- if (SupportsFormat<DXGI_FORMAT_B5G5R5A1_UNORM,false>(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else if (SupportsFormat<DXGI_FORMAT_B5G5R5A1_UNORM,true>(renderer11DeviceCaps))
+ if (SupportsFormat(DXGI_FORMAT_B5G5R5A1_UNORM, deviceCaps))
{
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_B5G5R5A1_UNORM,
- DXGI_FORMAT_B5G5R5A1_UNORM,
- DXGI_FORMAT_B5G5R5A1_UNORM,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
+ static constexpr Format info(GL_RGB5_A1,
+ angle::Format::ID::B5G5R5A1_UNORM,
+ DXGI_FORMAT_B5G5R5A1_UNORM,
+ DXGI_FORMAT_B5G5R5A1_UNORM,
+ DXGI_FORMAT_B5G5R5A1_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_B5G5R5A1_UNORM,
+ GL_RGBA8,
+ nullptr);
+ return info;
}
else
{
- break;
+ static constexpr Format info(GL_RGB5_A1,
+ angle::Format::ID::R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ GL_RGBA8,
+ nullptr);
+ return info;
}
}
case GL_RGB8:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RGB8,
+ angle::Format::ID::R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ GL_RGBA8,
+ Initialize4ComponentData<GLubyte, 0x00, 0x00, 0x00, 0xFF>);
+ return info;
}
case GL_RGB8I:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8B8A8_SINT,
- DXGI_FORMAT_R8G8B8A8_SINT,
- DXGI_FORMAT_R8G8B8A8_SINT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RGB8I,
+ angle::Format::ID::R8G8B8A8_SINT,
+ DXGI_FORMAT_R8G8B8A8_SINT,
+ DXGI_FORMAT_R8G8B8A8_SINT,
+ DXGI_FORMAT_R8G8B8A8_SINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8B8A8_SINT,
+ GL_RGBA8I,
+ Initialize4ComponentData<GLbyte, 0x00, 0x00, 0x00, 0x01>);
+ return info;
}
case GL_RGB8UI:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8B8A8_UINT,
- DXGI_FORMAT_R8G8B8A8_UINT,
- DXGI_FORMAT_R8G8B8A8_UINT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RGB8UI,
+ angle::Format::ID::R8G8B8A8_UINT,
+ DXGI_FORMAT_R8G8B8A8_UINT,
+ DXGI_FORMAT_R8G8B8A8_UINT,
+ DXGI_FORMAT_R8G8B8A8_UINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8B8A8_UINT,
+ GL_RGBA8UI,
+ Initialize4ComponentData<GLubyte, 0x00, 0x00, 0x00, 0x01>);
+ return info;
}
case GL_RGB8_SNORM:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8B8A8_SNORM,
- DXGI_FORMAT_R8G8B8A8_SNORM,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RGB8_SNORM,
+ angle::Format::ID::R8G8B8A8_SNORM,
+ DXGI_FORMAT_R8G8B8A8_SNORM,
+ DXGI_FORMAT_R8G8B8A8_SNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8B8A8_SNORM,
+ GL_RGBA8_SNORM,
+ Initialize4ComponentData<GLbyte, 0x00, 0x00, 0x00, 0x7F>);
+ return info;
}
case GL_RGB9_E5:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R9G9B9E5_SHAREDEXP,
- DXGI_FORMAT_R9G9B9E5_SHAREDEXP,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RGB9_E5,
+ angle::Format::ID::R9G9B9E5_SHAREDEXP,
+ DXGI_FORMAT_R9G9B9E5_SHAREDEXP,
+ DXGI_FORMAT_R9G9B9E5_SHAREDEXP,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R9G9B9E5_SHAREDEXP,
+ GL_RGBA16F_EXT,
+ nullptr);
+ return info;
}
case GL_RGBA:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RGBA,
+ angle::Format::ID::R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ GL_RGBA8,
+ nullptr);
+ return info;
}
case GL_RGBA16F:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R16G16B16A16_FLOAT,
- DXGI_FORMAT_R16G16B16A16_FLOAT,
- DXGI_FORMAT_R16G16B16A16_FLOAT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RGBA16F,
+ angle::Format::ID::R16G16B16A16_FLOAT,
+ DXGI_FORMAT_R16G16B16A16_FLOAT,
+ DXGI_FORMAT_R16G16B16A16_FLOAT,
+ DXGI_FORMAT_R16G16B16A16_FLOAT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R16G16B16A16_FLOAT,
+ GL_RGBA16F,
+ nullptr);
+ return info;
}
case GL_RGBA16I:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R16G16B16A16_SINT,
- DXGI_FORMAT_R16G16B16A16_SINT,
- DXGI_FORMAT_R16G16B16A16_SINT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RGBA16I,
+ angle::Format::ID::R16G16B16A16_SINT,
+ DXGI_FORMAT_R16G16B16A16_SINT,
+ DXGI_FORMAT_R16G16B16A16_SINT,
+ DXGI_FORMAT_R16G16B16A16_SINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R16G16B16A16_SINT,
+ GL_RGBA16I,
+ nullptr);
+ return info;
}
case GL_RGBA16UI:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R16G16B16A16_UINT,
- DXGI_FORMAT_R16G16B16A16_UINT,
- DXGI_FORMAT_R16G16B16A16_UINT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RGBA16UI,
+ angle::Format::ID::R16G16B16A16_UINT,
+ DXGI_FORMAT_R16G16B16A16_UINT,
+ DXGI_FORMAT_R16G16B16A16_UINT,
+ DXGI_FORMAT_R16G16B16A16_UINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R16G16B16A16_UINT,
+ GL_RGBA16UI,
+ nullptr);
+ return info;
+ }
+ case GL_RGBA16_EXT:
+ {
+ static constexpr Format info(GL_RGBA16_EXT,
+ angle::Format::ID::R16G16B16A16_UNORM,
+ DXGI_FORMAT_R16G16B16A16_UNORM,
+ DXGI_FORMAT_R16G16B16A16_UNORM,
+ DXGI_FORMAT_R16G16B16A16_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R16G16B16A16_UNORM,
+ GL_RGBA16_EXT,
+ nullptr);
+ return info;
+ }
+ case GL_RGBA16_SNORM_EXT:
+ {
+ static constexpr Format info(GL_RGBA16_SNORM_EXT,
+ angle::Format::ID::R16G16B16A16_SNORM,
+ DXGI_FORMAT_R16G16B16A16_SNORM,
+ DXGI_FORMAT_R16G16B16A16_SNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R16G16B16A16_SNORM,
+ GL_RGBA16_SNORM_EXT,
+ nullptr);
+ return info;
}
case GL_RGBA32F:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R32G32B32A32_FLOAT,
- DXGI_FORMAT_R32G32B32A32_FLOAT,
- DXGI_FORMAT_R32G32B32A32_FLOAT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RGBA32F,
+ angle::Format::ID::R32G32B32A32_FLOAT,
+ DXGI_FORMAT_R32G32B32A32_FLOAT,
+ DXGI_FORMAT_R32G32B32A32_FLOAT,
+ DXGI_FORMAT_R32G32B32A32_FLOAT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R32G32B32A32_FLOAT,
+ GL_RGBA32F,
+ nullptr);
+ return info;
}
case GL_RGBA32I:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R32G32B32A32_SINT,
- DXGI_FORMAT_R32G32B32A32_SINT,
- DXGI_FORMAT_R32G32B32A32_SINT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RGBA32I,
+ angle::Format::ID::R32G32B32A32_SINT,
+ DXGI_FORMAT_R32G32B32A32_SINT,
+ DXGI_FORMAT_R32G32B32A32_SINT,
+ DXGI_FORMAT_R32G32B32A32_SINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R32G32B32A32_SINT,
+ GL_RGBA32I,
+ nullptr);
+ return info;
}
case GL_RGBA32UI:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R32G32B32A32_UINT,
- DXGI_FORMAT_R32G32B32A32_UINT,
- DXGI_FORMAT_R32G32B32A32_UINT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RGBA32UI,
+ angle::Format::ID::R32G32B32A32_UINT,
+ DXGI_FORMAT_R32G32B32A32_UINT,
+ DXGI_FORMAT_R32G32B32A32_UINT,
+ DXGI_FORMAT_R32G32B32A32_UINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R32G32B32A32_UINT,
+ GL_RGBA32UI,
+ nullptr);
+ return info;
}
case GL_RGBA4:
{
- if (SupportsFormat<DXGI_FORMAT_B4G4R4A4_UNORM,false>(renderer11DeviceCaps))
+ if (SupportsFormat(DXGI_FORMAT_B4G4R4A4_UNORM, deviceCaps))
{
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else if (SupportsFormat<DXGI_FORMAT_B4G4R4A4_UNORM,true>(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_B4G4R4A4_UNORM,
- DXGI_FORMAT_B4G4R4A4_UNORM,
- DXGI_FORMAT_B4G4R4A4_UNORM,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
+ static constexpr Format info(GL_RGBA4,
+ angle::Format::ID::B4G4R4A4_UNORM,
+ DXGI_FORMAT_B4G4R4A4_UNORM,
+ DXGI_FORMAT_B4G4R4A4_UNORM,
+ DXGI_FORMAT_B4G4R4A4_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_B4G4R4A4_UNORM,
+ GL_RGBA4,
+ nullptr);
+ return info;
}
else
{
- break;
+ static constexpr Format info(GL_RGBA4,
+ angle::Format::ID::R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ GL_RGBA8,
+ nullptr);
+ return info;
}
}
case GL_RGBA8:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_R8G8B8A8_UNORM,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RGBA8,
+ angle::Format::ID::R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8B8A8_UNORM,
+ GL_RGBA8,
+ nullptr);
+ return info;
}
case GL_RGBA8I:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8B8A8_SINT,
- DXGI_FORMAT_R8G8B8A8_SINT,
- DXGI_FORMAT_R8G8B8A8_SINT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RGBA8I,
+ angle::Format::ID::R8G8B8A8_SINT,
+ DXGI_FORMAT_R8G8B8A8_SINT,
+ DXGI_FORMAT_R8G8B8A8_SINT,
+ DXGI_FORMAT_R8G8B8A8_SINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8B8A8_SINT,
+ GL_RGBA8I,
+ nullptr);
+ return info;
}
case GL_RGBA8UI:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8B8A8_UINT,
- DXGI_FORMAT_R8G8B8A8_UINT,
- DXGI_FORMAT_R8G8B8A8_UINT,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RGBA8UI,
+ angle::Format::ID::R8G8B8A8_UINT,
+ DXGI_FORMAT_R8G8B8A8_UINT,
+ DXGI_FORMAT_R8G8B8A8_UINT,
+ DXGI_FORMAT_R8G8B8A8_UINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8B8A8_UINT,
+ GL_RGBA8UI,
+ nullptr);
+ return info;
}
case GL_RGBA8_SNORM:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8B8A8_SNORM,
- DXGI_FORMAT_R8G8B8A8_SNORM,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_RGBA8_SNORM,
+ angle::Format::ID::R8G8B8A8_SNORM,
+ DXGI_FORMAT_R8G8B8A8_SNORM,
+ DXGI_FORMAT_R8G8B8A8_SNORM,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8B8A8_SNORM,
+ GL_RGBA8_SNORM,
+ nullptr);
+ return info;
}
case GL_SRGB8:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
- DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_SRGB8,
+ angle::Format::ID::R8G8B8A8_UNORM_SRGB,
+ DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
+ DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
+ DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
+ GL_SRGB8_ALPHA8,
+ Initialize4ComponentData<GLubyte, 0x00, 0x00, 0x00, 0xFF>);
+ return info;
}
case GL_SRGB8_ALPHA8:
{
- if (AnyDevice(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
- DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
- DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
- DXGI_FORMAT_UNKNOWN);
- return textureFormat;
- }
- else
- {
- break;
- }
+ static constexpr Format info(GL_SRGB8_ALPHA8,
+ angle::Format::ID::R8G8B8A8_UNORM_SRGB,
+ DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
+ DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
+ DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_R8G8B8A8_UNORM_SRGB,
+ GL_SRGB8_ALPHA8,
+ nullptr);
+ return info;
}
case GL_STENCIL_INDEX8:
{
- if (OnlyFL9_3(renderer11DeviceCaps))
+ if (OnlyFL10Plus(deviceCaps))
{
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_D24_UNORM_S8_UINT,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_D24_UNORM_S8_UINT);
- return textureFormat;
- }
- else if (OnlyFL10Plus(renderer11DeviceCaps))
- {
- static const TextureFormat textureFormat = GetD3D11FormatInfo(internalFormat,
- DXGI_FORMAT_R24G8_TYPELESS,
- DXGI_FORMAT_X24_TYPELESS_G8_UINT,
- DXGI_FORMAT_UNKNOWN,
- DXGI_FORMAT_D24_UNORM_S8_UINT);
- return textureFormat;
+ static constexpr Format info(GL_STENCIL_INDEX8,
+ angle::Format::ID::D24_UNORM_S8_UINT,
+ DXGI_FORMAT_R24G8_TYPELESS,
+ DXGI_FORMAT_R24_UNORM_X8_TYPELESS,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_D24_UNORM_S8_UINT,
+ DXGI_FORMAT_R24_UNORM_X8_TYPELESS,
+ GL_RGBA32F,
+ nullptr);
+ return info;
}
else
{
- break;
+ static constexpr Format info(GL_STENCIL_INDEX8,
+ angle::Format::ID::D24_UNORM_S8_UINT,
+ DXGI_FORMAT_D24_UNORM_S8_UINT,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_UNKNOWN,
+ DXGI_FORMAT_D24_UNORM_S8_UINT,
+ DXGI_FORMAT_UNKNOWN,
+ GL_RGBA32F,
+ nullptr);
+ return info;
}
}
@@ -1782,9 +1928,10 @@ const TextureFormat &GetTextureFormatInfo(GLenum internalFormat,
}
// clang-format on
- static const TextureFormat defaultInfo;
+ UNREACHABLE();
+ static constexpr Format defaultInfo;
return defaultInfo;
-} // GetTextureFormatInfo
+}
} // namespace d3d11
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/texture_format_table_utils.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/texture_format_table_utils.h
new file mode 100644
index 0000000000..d5351ff882
--- /dev/null
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/texture_format_table_utils.h
@@ -0,0 +1,85 @@
+//
+// Copyright 2016 The ANGLE Project Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+//
+// Helper routines for the D3D11 texture format table.
+
+#ifndef LIBANGLE_RENDERER_D3D_D3D11_TEXTURE_FORMAT_TABLE_UTILS_H_
+#define LIBANGLE_RENDERER_D3D_D3D11_TEXTURE_FORMAT_TABLE_UTILS_H_
+
+#include "libANGLE/renderer/d3d/d3d11/Renderer11.h"
+
+namespace rx
+{
+
+namespace d3d11
+{
+
+using FormatSupportFunction = bool (*)(const Renderer11DeviceCaps &);
+
+inline bool OnlyFL10Plus(const Renderer11DeviceCaps &deviceCaps)
+{
+ return (deviceCaps.featureLevel >= D3D_FEATURE_LEVEL_10_0);
+}
+
+inline bool OnlyFL9_3(const Renderer11DeviceCaps &deviceCaps)
+{
+ return (deviceCaps.featureLevel == D3D_FEATURE_LEVEL_9_3);
+}
+
+inline bool SupportsFormat(DXGI_FORMAT format, const Renderer11DeviceCaps &deviceCaps)
+{
+ // Must support texture, SRV and RTV support
+ UINT mustSupport = D3D11_FORMAT_SUPPORT_TEXTURE2D | D3D11_FORMAT_SUPPORT_TEXTURECUBE |
+ D3D11_FORMAT_SUPPORT_SHADER_SAMPLE | D3D11_FORMAT_SUPPORT_MIP |
+ D3D11_FORMAT_SUPPORT_RENDER_TARGET;
+ UINT minimumRequiredSamples = 0;
+
+ if (d3d11_gl::GetMaximumClientVersion(deviceCaps.featureLevel).major > 2)
+ {
+ mustSupport |= D3D11_FORMAT_SUPPORT_TEXTURE3D;
+
+ // RGBA4, RGB5A1 and RGB565 are all required multisampled renderbuffer formats in ES3 and
+ // need to support a minimum of 4 samples.
+ minimumRequiredSamples = 4;
+ }
+
+ bool fullSupport = false;
+ if (format == DXGI_FORMAT_B5G6R5_UNORM)
+ {
+ // All hardware that supports DXGI_FORMAT_B5G6R5_UNORM should support autogen mipmaps, but
+ // check anyway.
+ mustSupport |= D3D11_FORMAT_SUPPORT_MIP_AUTOGEN;
+ fullSupport = ((deviceCaps.B5G6R5support & mustSupport) == mustSupport) &&
+ deviceCaps.B5G6R5maxSamples >= minimumRequiredSamples;
+ }
+ else if (format == DXGI_FORMAT_B4G4R4A4_UNORM)
+ {
+ fullSupport = ((deviceCaps.B4G4R4A4support & mustSupport) == mustSupport) &&
+ deviceCaps.B4G4R4A4maxSamples >= minimumRequiredSamples;
+ }
+ else if (format == DXGI_FORMAT_B5G5R5A1_UNORM)
+ {
+ fullSupport = ((deviceCaps.B5G5R5A1support & mustSupport) == mustSupport) &&
+ deviceCaps.B5G5R5A1maxSamples >= minimumRequiredSamples;
+ }
+ else
+ {
+ UNREACHABLE();
+ return false;
+ }
+
+ // This means that ANGLE would like to use the entry in the map if the inputted DXGI format
+ // *IS* supported.
+ // e.g. the entry might map GL_RGB5_A1 to DXGI_FORMAT_B5G5R5A1, which should only be used if
+ // DXGI_FORMAT_B5G5R5A1 is supported.
+ // In this case, we should only return 'true' if the format *IS* supported.
+ return fullSupport;
+}
+
+} // namespace d3d11
+
+} // namespace rx
+
+#endif // LIBANGLE_RENDERER_D3D_D3D11_TEXTURE_FORMAT_TABLE_UTILS_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/win32/NativeWindow.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/win32/NativeWindow11Win32.cpp
index da6460b136..5394e3d3e7 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/win32/NativeWindow.cpp
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/win32/NativeWindow11Win32.cpp
@@ -1,76 +1,70 @@
//
-// Copyright (c) 2014 The ANGLE Project Authors. All rights reserved.
+// Copyright (c) 2016 The ANGLE Project Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
//
-// NativeWindow.cpp: Handler for managing HWND native window types.
+// NativeWindow11Win32.cpp: Implementation of NativeWindow11 using win32 window APIs.
-#include "libANGLE/renderer/d3d/d3d11/NativeWindow.h"
+#include "libANGLE/renderer/d3d/d3d11/win32/NativeWindow11Win32.h"
#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
#include "common/debug.h"
#include <initguid.h>
-#if !defined(__MINGW32__)
#include <dcomp.h>
-#endif
namespace rx
{
-NativeWindow::NativeWindow(EGLNativeWindowType window,
- const egl::Config *config,
- bool directComposition)
- : mWindow(window),
+NativeWindow11Win32::NativeWindow11Win32(EGLNativeWindowType window,
+ bool hasAlpha,
+ bool directComposition)
+ : NativeWindow11(window),
mDirectComposition(directComposition),
+ mHasAlpha(hasAlpha),
mDevice(nullptr),
mCompositionTarget(nullptr),
- mVisual(nullptr),
- mConfig(config)
+ mVisual(nullptr)
{
}
-NativeWindow::~NativeWindow()
+NativeWindow11Win32::~NativeWindow11Win32()
{
-#if !defined(__MINGW32__)
SafeRelease(mCompositionTarget);
SafeRelease(mDevice);
SafeRelease(mVisual);
-#endif
}
-bool NativeWindow::initialize()
+bool NativeWindow11Win32::initialize()
{
return true;
}
-bool NativeWindow::getClientRect(LPRECT rect)
+bool NativeWindow11Win32::getClientRect(LPRECT rect) const
{
- return GetClientRect(mWindow, rect) == TRUE;
+ return GetClientRect(getNativeWindow(), rect) == TRUE;
}
-bool NativeWindow::isIconic()
+bool NativeWindow11Win32::isIconic() const
{
- return IsIconic(mWindow) == TRUE;
+ return IsIconic(getNativeWindow()) == TRUE;
}
-bool NativeWindow::isValidNativeWindow(EGLNativeWindowType window)
+HRESULT NativeWindow11Win32::createSwapChain(ID3D11Device *device,
+ IDXGIFactory *factory,
+ DXGI_FORMAT format,
+ UINT width,
+ UINT height,
+ UINT samples,
+ IDXGISwapChain **swapChain)
{
- return IsWindow(window) == TRUE;
-}
-
-#if defined(ANGLE_ENABLE_D3D11)
-HRESULT NativeWindow::createSwapChain(ID3D11Device* device, DXGIFactory* factory,
- DXGI_FORMAT format, unsigned int width, unsigned int height,
- DXGISwapChain** swapChain)
-{
- if (device == NULL || factory == NULL || swapChain == NULL || width == 0 || height == 0)
+ if (device == nullptr || factory == nullptr || swapChain == nullptr || width == 0 ||
+ height == 0)
{
return E_INVALIDARG;
}
-#if !defined(__MINGW32__)
if (mDirectComposition)
{
HMODULE dcomp = ::GetModuleHandle(TEXT("dcomp.dll"));
@@ -104,7 +98,8 @@ HRESULT NativeWindow::createSwapChain(ID3D11Device* device, DXGIFactory* factory
if (!mCompositionTarget)
{
- HRESULT result = mDevice->CreateTargetForHwnd(mWindow, TRUE, &mCompositionTarget);
+ HRESULT result =
+ mDevice->CreateTargetForHwnd(getNativeWindow(), TRUE, &mCompositionTarget);
if (FAILED(result))
{
return result;
@@ -127,21 +122,21 @@ HRESULT NativeWindow::createSwapChain(ID3D11Device* device, DXGIFactory* factory
swapChainDesc.Format = format;
swapChainDesc.Stereo = FALSE;
swapChainDesc.SampleDesc.Count = 1;
- swapChainDesc.SampleDesc.Quality = 0;
+ swapChainDesc.SampleDesc.Quality = 0;
swapChainDesc.BufferUsage =
DXGI_USAGE_RENDER_TARGET_OUTPUT | DXGI_USAGE_BACK_BUFFER | DXGI_USAGE_SHADER_INPUT;
- swapChainDesc.BufferCount = 2;
- swapChainDesc.Scaling = DXGI_SCALING_STRETCH;
+ swapChainDesc.BufferCount = 2;
+ swapChainDesc.Scaling = DXGI_SCALING_STRETCH;
swapChainDesc.SwapEffect = DXGI_SWAP_EFFECT_FLIP_SEQUENTIAL;
swapChainDesc.AlphaMode =
- mConfig->alphaSize == 0 ? DXGI_ALPHA_MODE_IGNORE : DXGI_ALPHA_MODE_PREMULTIPLIED;
+ mHasAlpha ? DXGI_ALPHA_MODE_PREMULTIPLIED : DXGI_ALPHA_MODE_IGNORE;
swapChainDesc.Flags = 0;
IDXGISwapChain1 *swapChain1 = nullptr;
HRESULT result =
factory2->CreateSwapChainForComposition(device, &swapChainDesc, nullptr, &swapChain1);
if (SUCCEEDED(result))
{
- *swapChain = static_cast<DXGISwapChain *>(swapChain1);
+ *swapChain = static_cast<IDXGISwapChain *>(swapChain1);
}
mVisual->SetContent(swapChain1);
mCompositionTarget->SetRoot(mVisual);
@@ -149,72 +144,74 @@ HRESULT NativeWindow::createSwapChain(ID3D11Device* device, DXGIFactory* factory
return result;
}
- // Use IDXGIFactory2::CreateSwapChainForHwnd if DXGI 1.2 is available to create a DXGI_SWAP_EFFECT_SEQUENTIAL swap chain.
+ // Use IDXGIFactory2::CreateSwapChainForHwnd if DXGI 1.2 is available to create a
+ // DXGI_SWAP_EFFECT_SEQUENTIAL swap chain.
IDXGIFactory2 *factory2 = d3d11::DynamicCastComObject<IDXGIFactory2>(factory);
if (factory2 != nullptr)
{
- DXGI_SWAP_CHAIN_DESC1 swapChainDesc = { 0 };
- swapChainDesc.Width = width;
- swapChainDesc.Height = height;
- swapChainDesc.Format = format;
- swapChainDesc.Stereo = FALSE;
- swapChainDesc.SampleDesc.Count = 1;
- swapChainDesc.SampleDesc.Quality = 0;
+ DXGI_SWAP_CHAIN_DESC1 swapChainDesc = {0};
+ swapChainDesc.Width = width;
+ swapChainDesc.Height = height;
+ swapChainDesc.Format = format;
+ swapChainDesc.Stereo = FALSE;
+ swapChainDesc.SampleDesc.Count = samples;
+ swapChainDesc.SampleDesc.Quality = 0;
swapChainDesc.BufferUsage =
DXGI_USAGE_RENDER_TARGET_OUTPUT | DXGI_USAGE_SHADER_INPUT | DXGI_USAGE_BACK_BUFFER;
- swapChainDesc.BufferCount = 1;
- swapChainDesc.Scaling = DXGI_SCALING_STRETCH;
- swapChainDesc.SwapEffect = DXGI_SWAP_EFFECT_SEQUENTIAL;
- swapChainDesc.AlphaMode = DXGI_ALPHA_MODE_UNSPECIFIED;
- swapChainDesc.Flags = 0;
+ swapChainDesc.BufferCount = 1;
+ swapChainDesc.Scaling = DXGI_SCALING_STRETCH;
+ swapChainDesc.SwapEffect = DXGI_SWAP_EFFECT_SEQUENTIAL;
+ swapChainDesc.AlphaMode = DXGI_ALPHA_MODE_UNSPECIFIED;
+ swapChainDesc.Flags = 0;
IDXGISwapChain1 *swapChain1 = nullptr;
- HRESULT result = factory2->CreateSwapChainForHwnd(device, mWindow, &swapChainDesc, nullptr, nullptr, &swapChain1);
+ HRESULT result = factory2->CreateSwapChainForHwnd(device, getNativeWindow(), &swapChainDesc,
+ nullptr, nullptr, &swapChain1);
if (SUCCEEDED(result))
{
- const HRESULT makeWindowAssociationResult = factory->MakeWindowAssociation(mWindow, DXGI_MWA_NO_ALT_ENTER);
- UNUSED_VARIABLE(makeWindowAssociationResult);
- *swapChain = static_cast<DXGISwapChain*>(swapChain1);
+ factory2->MakeWindowAssociation(getNativeWindow(), DXGI_MWA_NO_ALT_ENTER);
+ *swapChain = static_cast<IDXGISwapChain *>(swapChain1);
}
SafeRelease(factory2);
return result;
}
-#endif // !__MINGW32__
-
- DXGI_SWAP_CHAIN_DESC swapChainDesc = {};
- swapChainDesc.BufferCount = 1;
- swapChainDesc.BufferDesc.Format = format;
- swapChainDesc.BufferDesc.Width = width;
- swapChainDesc.BufferDesc.Height = height;
- swapChainDesc.BufferDesc.Scaling = DXGI_MODE_SCALING_UNSPECIFIED;
- swapChainDesc.BufferDesc.ScanlineOrdering = DXGI_MODE_SCANLINE_ORDER_UNSPECIFIED;
- swapChainDesc.BufferDesc.RefreshRate.Numerator = 0;
+
+ DXGI_SWAP_CHAIN_DESC swapChainDesc = {};
+ swapChainDesc.BufferCount = 1;
+ swapChainDesc.BufferDesc.Format = format;
+ swapChainDesc.BufferDesc.Width = width;
+ swapChainDesc.BufferDesc.Height = height;
+ swapChainDesc.BufferDesc.Scaling = DXGI_MODE_SCALING_UNSPECIFIED;
+ swapChainDesc.BufferDesc.ScanlineOrdering = DXGI_MODE_SCANLINE_ORDER_UNSPECIFIED;
+ swapChainDesc.BufferDesc.RefreshRate.Numerator = 0;
swapChainDesc.BufferDesc.RefreshRate.Denominator = 1;
swapChainDesc.BufferUsage =
DXGI_USAGE_RENDER_TARGET_OUTPUT | DXGI_USAGE_SHADER_INPUT | DXGI_USAGE_BACK_BUFFER;
- swapChainDesc.Flags = 0;
- swapChainDesc.OutputWindow = mWindow;
- swapChainDesc.SampleDesc.Count = 1;
+ swapChainDesc.Flags = 0;
+ swapChainDesc.OutputWindow = getNativeWindow();
+ swapChainDesc.SampleDesc.Count = samples;
swapChainDesc.SampleDesc.Quality = 0;
- swapChainDesc.Windowed = TRUE;
- swapChainDesc.SwapEffect = DXGI_SWAP_EFFECT_DISCARD;
+ swapChainDesc.Windowed = TRUE;
+ swapChainDesc.SwapEffect = DXGI_SWAP_EFFECT_DISCARD;
- const HRESULT result = factory->CreateSwapChain(device, &swapChainDesc, swapChain);
+ HRESULT result = factory->CreateSwapChain(device, &swapChainDesc, swapChain);
if (SUCCEEDED(result))
{
- const HRESULT makeWindowAssociationResult = factory->MakeWindowAssociation(mWindow, DXGI_MWA_NO_ALT_ENTER);
- UNUSED_VARIABLE(makeWindowAssociationResult);
+ factory->MakeWindowAssociation(getNativeWindow(), DXGI_MWA_NO_ALT_ENTER);
}
return result;
}
-#endif
-void NativeWindow::commitChange()
+void NativeWindow11Win32::commitChange()
{
-#if !defined(__MINGW32__)
if (mDevice)
{
mDevice->Commit();
}
-#endif
}
+
+// static
+bool NativeWindow11Win32::IsValidNativeWindow(EGLNativeWindowType window)
+{
+ return IsWindow(window) == TRUE;
}
+} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/win32/NativeWindow11Win32.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/win32/NativeWindow11Win32.h
new file mode 100644
index 0000000000..baeba6a347
--- /dev/null
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/win32/NativeWindow11Win32.h
@@ -0,0 +1,53 @@
+//
+// Copyright (c) 2016 The ANGLE Project Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+//
+
+// NativeWindow11Win32.h: Implementation of NativeWindow11 using win32 window APIs.
+
+#ifndef LIBANGLE_RENDERER_D3D_D3D11_WIN32_NATIVEWINDOW11WIN32_H_
+#define LIBANGLE_RENDERER_D3D_D3D11_WIN32_NATIVEWINDOW11WIN32_H_
+
+#include "libANGLE/renderer/d3d/d3d11/NativeWindow11.h"
+
+typedef interface IDCompositionDevice IDCompositionDevice;
+typedef interface IDCompositionTarget IDCompositionTarget;
+typedef interface IDCompositionVisual IDCompositionVisual;
+
+namespace rx
+{
+
+class NativeWindow11Win32 : public NativeWindow11
+{
+ public:
+ NativeWindow11Win32(EGLNativeWindowType window, bool hasAlpha, bool directComposition);
+ ~NativeWindow11Win32() override;
+
+ bool initialize() override;
+ bool getClientRect(LPRECT rect) const override;
+ bool isIconic() const override;
+
+ HRESULT createSwapChain(ID3D11Device *device,
+ IDXGIFactory *factory,
+ DXGI_FORMAT format,
+ UINT width,
+ UINT height,
+ UINT samples,
+ IDXGISwapChain **swapChain) override;
+
+ void commitChange() override;
+
+ static bool IsValidNativeWindow(EGLNativeWindowType window);
+
+ private:
+ bool mDirectComposition;
+ bool mHasAlpha;
+ IDCompositionDevice *mDevice;
+ IDCompositionTarget *mCompositionTarget;
+ IDCompositionVisual *mVisual;
+};
+
+} // namespace rx
+
+#endif // LIBANGLE_RENDERER_D3D_D3D11_WIN32_NATIVEWINDOW11WIN32_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/CoreWindowNativeWindow.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/CoreWindowNativeWindow.cpp
index f401db614b..1ef90e7b09 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/CoreWindowNativeWindow.cpp
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/CoreWindowNativeWindow.cpp
@@ -8,6 +8,8 @@
#include "libANGLE/renderer/d3d/d3d11/winrt/CoreWindowNativeWindow.h"
+#include <windows.graphics.display.h>
+
using namespace ABI::Windows::Foundation::Collections;
namespace rx
@@ -19,7 +21,6 @@ CoreWindowNativeWindow::~CoreWindowNativeWindow()
bool CoreWindowNativeWindow::initialize(EGLNativeWindowType window, IPropertySet *propertySet)
{
- mOrientationChangedEventToken.value = 0;
ComPtr<IPropertySet> props = propertySet;
ComPtr<IInspectable> win = window;
SIZE swapChainSize = {};
@@ -63,7 +64,8 @@ bool CoreWindowNativeWindow::initialize(EGLNativeWindowType window, IPropertySet
// A EGLRenderSurfaceSizeProperty and a EGLRenderResolutionScaleProperty can't both be specified
if (mSwapChainScaleSpecified && mSwapChainSizeSpecified)
{
- ERR("It is invalid to specify both an EGLRenderSurfaceSizeProperty and a EGLRenderResolutionScaleProperty.");
+ ERR() << "It is invalid to specify both an EGLRenderSurfaceSizeProperty and a "
+ "EGLRenderResolutionScaleProperty.";
return false;
}
}
@@ -87,28 +89,18 @@ bool CoreWindowNativeWindow::initialize(EGLNativeWindowType window, IPropertySet
}
else
{
- SIZE coreWindowSize;
+ Size coreWindowSize;
result = GetCoreWindowSizeInPixels(mCoreWindow, &coreWindowSize);
if (SUCCEEDED(result))
{
- mClientRect = { 0, 0, static_cast<long>(coreWindowSize.cx * mSwapChainScale), static_cast<long>(coreWindowSize.cy * mSwapChainScale) };
+ mClientRect = clientRect(coreWindowSize);
}
}
}
if (SUCCEEDED(result))
{
- ComPtr<ABI::Windows::Graphics::Display::IDisplayInformationStatics> displayInformation;
- result = GetActivationFactory(HStringReference(RuntimeClass_Windows_Graphics_Display_DisplayInformation).Get(), &displayInformation);
- if (SUCCEEDED(result))
- {
- result = displayInformation->GetForCurrentView(&mDisplayInformation);
- }
- }
-
- if (SUCCEEDED(result))
- {
mNewClientRect = mClientRect;
mClientRectChanged = false;
return registerForSizeChangeEvents();
@@ -126,16 +118,6 @@ bool CoreWindowNativeWindow::registerForSizeChangeEvents()
result = mCoreWindow->add_SizeChanged(sizeChangedHandler.Get(), &mSizeChangedEventToken);
}
-#if defined(ANGLE_ENABLE_WINDOWS_STORE) && (WINAPI_FAMILY == WINAPI_FAMILY_PHONE_APP)
- ComPtr<IDisplayOrientationEventHandler> orientationChangedHandler;
- result = sizeChangedHandler.As(&orientationChangedHandler);
- if (SUCCEEDED(result))
- {
- result = mDisplayInformation->add_OrientationChanged(orientationChangedHandler.Get(), &mOrientationChangedEventToken);
- orientationChangedHandler->Invoke(mDisplayInformation.Get(), nullptr);
- }
-#endif
-
if (SUCCEEDED(result))
{
return true;
@@ -150,34 +132,26 @@ void CoreWindowNativeWindow::unregisterForSizeChangeEvents()
{
(void)mCoreWindow->remove_SizeChanged(mSizeChangedEventToken);
}
-
-#if defined(ANGLE_ENABLE_WINDOWS_STORE) && (WINAPI_FAMILY == WINAPI_FAMILY_PHONE_APP)
- if (mDisplayInformation)
- {
- (void)mDisplayInformation->remove_OrientationChanged(mOrientationChangedEventToken);
- }
-#endif
-
mSizeChangedEventToken.value = 0;
- mOrientationChangedEventToken.value = 0;
}
HRESULT CoreWindowNativeWindow::createSwapChain(ID3D11Device *device,
- DXGIFactory *factory,
+ IDXGIFactory2 *factory,
DXGI_FORMAT format,
unsigned int width,
unsigned int height,
bool containsAlpha,
- DXGISwapChain **swapChain)
+ IDXGISwapChain1 **swapChain)
{
- if (device == NULL || factory == NULL || swapChain == NULL || width == 0 || height == 0)
+ if (device == nullptr || factory == nullptr || swapChain == nullptr || width == 0 ||
+ height == 0)
{
return E_INVALIDARG;
}
DXGI_SWAP_CHAIN_DESC1 swapChainDesc = { 0 };
- swapChainDesc.Width = mRotationFlags ? height : width;
- swapChainDesc.Height = mRotationFlags ? width : height;
+ swapChainDesc.Width = width;
+ swapChainDesc.Height = height;
swapChainDesc.Format = format;
swapChainDesc.Stereo = FALSE;
swapChainDesc.SampleDesc.Count = 1;
@@ -195,17 +169,6 @@ HRESULT CoreWindowNativeWindow::createSwapChain(ID3D11Device *device,
HRESULT result = factory->CreateSwapChainForCoreWindow(device, mCoreWindow.Get(), &swapChainDesc, nullptr, newSwapChain.ReleaseAndGetAddressOf());
if (SUCCEEDED(result))
{
-
-#if 0 //(WINAPI_FAMILY == WINAPI_FAMILY_PHONE_APP) // Qt: allow Windows Phone to resize, but don't modify the backing texture in the swap chain.
- // Test if swapchain supports resize. On Windows Phone devices, this will return DXGI_ERROR_UNSUPPORTED. On
- // other devices DXGI_ERROR_INVALID_CALL should be returned because the combination of flags passed
- // (DXGI_SWAP_CHAIN_FLAG_NONPREROTATED | DXGI_SWAP_CHAIN_FLAG_GDI_COMPATIBLE) are invalid flag combinations.
- if (newSwapChain->ResizeBuffers(swapChainDesc.BufferCount, swapChainDesc.Width, swapChainDesc.Height, swapChainDesc.Format, DXGI_SWAP_CHAIN_FLAG_NONPREROTATED | DXGI_SWAP_CHAIN_FLAG_GDI_COMPATIBLE) == DXGI_ERROR_UNSUPPORTED)
- {
- mSupportsSwapChainResize = false;
- }
-#endif // (WINAPI_FAMILY == WINAPI_FAMILY_PHONE_APP)
-
result = newSwapChain.CopyTo(swapChain);
}
@@ -222,14 +185,16 @@ HRESULT CoreWindowNativeWindow::createSwapChain(ID3D11Device *device,
return result;
}
-inline HRESULT CoreWindowNativeWindow::scaleSwapChain(const Size &windowSize, const RECT &clientRect)
+inline HRESULT CoreWindowNativeWindow::scaleSwapChain(const Size &windowSize,
+ const RECT &clientRect)
{
// We don't need to do any additional work to scale CoreWindow swapchains.
// Using DXGI_SCALING_STRETCH to create the swapchain above does all the necessary work.
return S_OK;
}
-HRESULT GetCoreWindowSizeInPixels(const ComPtr<ABI::Windows::UI::Core::ICoreWindow>& coreWindow, SIZE *windowSize)
+HRESULT GetCoreWindowSizeInPixels(const ComPtr<ABI::Windows::UI::Core::ICoreWindow> &coreWindow,
+ Size *windowSize)
{
ABI::Windows::Foundation::Rect bounds;
HRESULT result = coreWindow->get_Bounds(&bounds);
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/CoreWindowNativeWindow.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/CoreWindowNativeWindow.h
index fc1cd124a1..21855c2c3b 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/CoreWindowNativeWindow.h
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/CoreWindowNativeWindow.h
@@ -12,10 +12,10 @@
#include "libANGLE/renderer/d3d/d3d11/winrt/InspectableNativeWindow.h"
#include <memory>
-#include <windows.graphics.display.h>
+
+#include <EGL/eglplatform.h>
typedef ABI::Windows::Foundation::__FITypedEventHandler_2_Windows__CUI__CCore__CCoreWindow_Windows__CUI__CCore__CWindowSizeChangedEventArgs_t IWindowSizeChangedEventHandler;
-typedef ABI::Windows::Foundation::__FITypedEventHandler_2_Windows__CGraphics__CDisplay__CDisplayInformation_IInspectable_t IDisplayOrientationEventHandler;
namespace rx
{
@@ -26,12 +26,12 @@ class CoreWindowNativeWindow : public InspectableNativeWindow, public std::enabl
bool initialize(EGLNativeWindowType window, IPropertySet *propertySet) override;
HRESULT createSwapChain(ID3D11Device *device,
- DXGIFactory *factory,
+ IDXGIFactory2 *factory,
DXGI_FORMAT format,
unsigned int width,
unsigned int height,
bool containsAlpha,
- DXGISwapChain **swapChain) override;
+ IDXGISwapChain1 **swapChain) override;
protected:
HRESULT scaleSwapChain(const Size &windowSize, const RECT &clientRect) override;
@@ -42,13 +42,11 @@ class CoreWindowNativeWindow : public InspectableNativeWindow, public std::enabl
private:
ComPtr<ABI::Windows::UI::Core::ICoreWindow> mCoreWindow;
ComPtr<IMap<HSTRING, IInspectable*>> mPropertyMap;
- ComPtr<ABI::Windows::Graphics::Display::IDisplayInformation> mDisplayInformation;
- EventRegistrationToken mOrientationChangedEventToken;
};
[uuid(7F924F66-EBAE-40E5-A10B-B8F35E245190)]
class CoreWindowSizeChangedHandler :
- public Microsoft::WRL::RuntimeClass<Microsoft::WRL::RuntimeClassFlags<Microsoft::WRL::ClassicCom>, IWindowSizeChangedEventHandler, IDisplayOrientationEventHandler>
+ public Microsoft::WRL::RuntimeClass<Microsoft::WRL::RuntimeClassFlags<Microsoft::WRL::ClassicCom>, IWindowSizeChangedEventHandler>
{
public:
CoreWindowSizeChangedHandler() { }
@@ -72,47 +70,21 @@ class CoreWindowSizeChangedHandler :
ABI::Windows::Foundation::Size windowSize;
if (SUCCEEDED(sizeChangedEventArgs->get_Size(&windowSize)))
{
- host->setNewClientSize(windowSize);
+ Size windowSizeInPixels = {ConvertDipsToPixels(windowSize.Width),
+ ConvertDipsToPixels(windowSize.Height)};
+ host->setNewClientSize(windowSizeInPixels);
}
}
return S_OK;
}
- IFACEMETHOD(Invoke)(ABI::Windows::Graphics::Display::IDisplayInformation *displayInformation, IInspectable *)
- {
- #if defined(ANGLE_ENABLE_WINDOWS_STORE) && (WINAPI_FAMILY == WINAPI_FAMILY_PHONE_APP)
- NativeWindow::RotationFlags flags = NativeWindow::RotateNone;
- ABI::Windows::Graphics::Display::DisplayOrientations orientation;
- if (SUCCEEDED(displayInformation->get_CurrentOrientation(&orientation)))
- {
- switch (orientation)
- {
- case ABI::Windows::Graphics::Display::DisplayOrientations_Landscape:
- flags = NativeWindow::RotateLeft;
- break;
- case ABI::Windows::Graphics::Display::DisplayOrientations_LandscapeFlipped:
- flags = NativeWindow::RotateRight;
- break;
- default:
- break;
- }
- }
- std::shared_ptr<InspectableNativeWindow> host = mHost.lock();
- if (host)
- {
- host->setRotationFlags(flags);
- }
- #endif
- return S_OK;
- }
-
-
private:
std::weak_ptr<InspectableNativeWindow> mHost;
};
-HRESULT GetCoreWindowSizeInPixels(const ComPtr<ABI::Windows::UI::Core::ICoreWindow>& coreWindow, SIZE *windowSize);
+HRESULT GetCoreWindowSizeInPixels(const ComPtr<ABI::Windows::UI::Core::ICoreWindow> &coreWindow,
+ Size *windowSize);
}
#endif // LIBANGLE_RENDERER_D3D_D3D11_WINRT_COREWINDOWNATIVEWINDOW_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/InspectableNativeWindow.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/InspectableNativeWindow.cpp
index aacfadd2f0..1bd796e58f 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/InspectableNativeWindow.cpp
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/InspectableNativeWindow.cpp
@@ -11,108 +11,6 @@
namespace rx
{
-NativeWindow::NativeWindow(EGLNativeWindowType window,
- const egl::Config *config,
- bool directComposition)
-{
- mWindow = window;
- mConfig = config;
-}
-
-NativeWindow::~NativeWindow()
-{
-}
-
-void NativeWindow::commitChange()
-{
-}
-
-bool NativeWindow::initialize()
-{
- // If the native window type is a IPropertySet, extract the
- // EGLNativeWindowType (IInspectable) and initialize the
- // proper host with this IPropertySet.
- ComPtr<ABI::Windows::Foundation::Collections::IPropertySet> propertySet;
- ComPtr<IInspectable> eglNativeWindow;
- if (IsEGLConfiguredPropertySet(mWindow, &propertySet, &eglNativeWindow))
- {
- // A property set was found and the EGLNativeWindowType was
- // retrieved. The mWindow member of the host to must be updated
- // to use the EGLNativeWindowType specified in the property set.
- // mWindow is treated as a raw pointer not an AddRef'd interface, so
- // the old mWindow does not need a Release() before this assignment.
- mWindow = eglNativeWindow.Get();
- }
-
- ComPtr<ABI::Windows::UI::Core::ICoreWindow> coreWindow;
- ComPtr<ABI::Windows::UI::Xaml::Controls::ISwapChainPanel> swapChainPanel;
- if (IsCoreWindow(mWindow, &coreWindow))
- {
- mImpl = std::make_shared<CoreWindowNativeWindow>();
- if (mImpl)
- {
- return mImpl->initialize(mWindow, propertySet.Get());
- }
- }
- else if (IsSwapChainPanel(mWindow, &swapChainPanel))
- {
- mImpl = std::make_shared<SwapChainPanelNativeWindow>();
- if (mImpl)
- {
- return mImpl->initialize(mWindow, propertySet.Get());
- }
- }
- else
- {
- ERR("Invalid IInspectable EGLNativeWindowType detected. Valid IInspectables include ICoreWindow, ISwapChainPanel and IPropertySet");
- }
-
- return false;
-}
-
-bool NativeWindow::getClientRect(RECT *rect)
-{
- if (mImpl)
- {
- return mImpl->getClientRect(rect);
- }
-
- return false;
-}
-
-#if defined(ANGLE_ENABLE_WINDOWS_STORE) && (WINAPI_FAMILY == WINAPI_FAMILY_PHONE_APP)
-NativeWindow::RotationFlags NativeWindow::rotationFlags() const
-{
- if (mImpl)
- {
- return mImpl->rotationFlags();
- }
-
- return NativeWindow::RotateNone;
-}
-#endif
-
-bool NativeWindow::isIconic()
-{
- return false;
-}
-
-bool NativeWindow::isValidNativeWindow(EGLNativeWindowType window)
-{
- return IsValidEGLNativeWindowType(window);
-}
-
-HRESULT NativeWindow::createSwapChain(ID3D11Device *device, DXGIFactory *factory, DXGI_FORMAT format, unsigned int width, unsigned int height, DXGISwapChain **swapChain)
-{
- if (mImpl)
- {
- bool containsAlpha = (mConfig->alphaSize > 0);
- return mImpl->createSwapChain(device, factory, format, width, height, containsAlpha,
- swapChain);
- }
-
- return E_UNEXPECTED;
-}
bool IsCoreWindow(EGLNativeWindowType window, ComPtr<ABI::Windows::UI::Core::ICoreWindow> *coreWindow)
{
@@ -127,7 +25,7 @@ bool IsCoreWindow(EGLNativeWindowType window, ComPtr<ABI::Windows::UI::Core::ICo
{
if (coreWindow != nullptr)
{
- *coreWindow = coreWin.Detach();
+ *coreWindow = coreWin;
}
return true;
}
@@ -148,7 +46,7 @@ bool IsSwapChainPanel(EGLNativeWindowType window, ComPtr<ABI::Windows::UI::Xaml:
{
if (swapChainPanel != nullptr)
{
- *swapChainPanel = panel.Detach();
+ *swapChainPanel = panel;
}
return true;
}
@@ -185,7 +83,8 @@ bool IsEGLConfiguredPropertySet(EGLNativeWindowType window, ABI::Windows::Founda
// considered invalid.
if (SUCCEEDED(result) && !hasEglNativeWindowPropertyKey)
{
- ERR("Could not find EGLNativeWindowTypeProperty in IPropertySet. Valid EGLNativeWindowTypeProperty values include ICoreWindow");
+ ERR() << "Could not find EGLNativeWindowTypeProperty in IPropertySet. Valid "
+ "EGLNativeWindowTypeProperty values include ICoreWindow";
return false;
}
@@ -219,18 +118,6 @@ bool IsEGLConfiguredPropertySet(EGLNativeWindowType window, ABI::Windows::Founda
return false;
}
-// A Valid EGLNativeWindowType IInspectable can only be:
-//
-// ICoreWindow
-// ISwapChainPanel
-// IPropertySet
-//
-// Anything else will be rejected as an invalid IInspectable.
-bool IsValidEGLNativeWindowType(EGLNativeWindowType window)
-{
- return IsCoreWindow(window) || IsSwapChainPanel(window) || IsEGLConfiguredPropertySet(window);
-}
-
// Retrieve an optional property from a property set
HRESULT GetOptionalPropertyValue(const ComPtr<ABI::Windows::Foundation::Collections::IMap<HSTRING, IInspectable*>> &propertyMap,
const wchar_t *propertyName,
@@ -381,7 +268,13 @@ HRESULT GetOptionalSinglePropertyValue(const ComPtr<ABI::Windows::Foundation::Co
return result;
}
-static float GetLogicalDpi()
+RECT InspectableNativeWindow::clientRect(const Size &size)
+{
+ return {0, 0, static_cast<long>(ConvertDipsToPixels(size.Width)),
+ static_cast<long>(ConvertDipsToPixels(size.Height))};
+}
+
+float GetLogicalDpi()
{
ComPtr<ABI::Windows::Graphics::Display::IDisplayPropertiesStatics> displayProperties;
float dpi = 96.0f;
@@ -396,7 +289,7 @@ static float GetLogicalDpi()
return dpi;
}
-long ConvertDipsToPixels(float dips)
+float ConvertDipsToPixels(float dips)
{
static const float dipsPerInch = 96.0f;
return lround((dips * GetLogicalDpi() / dipsPerInch));
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/InspectableNativeWindow.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/InspectableNativeWindow.h
index 2d58f1c00a..d81c3e5fb9 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/InspectableNativeWindow.h
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/InspectableNativeWindow.h
@@ -10,14 +10,18 @@
#ifndef LIBANGLE_RENDERER_D3D_D3D11_WINRT_INSPECTABLENATIVEWINDOW_H_
#define LIBANGLE_RENDERER_D3D_D3D11_WINRT_INSPECTABLENATIVEWINDOW_H_
-#include "libANGLE/renderer/d3d/d3d11/NativeWindow.h"
-
+#include "common/debug.h"
#include "common/platform.h"
#include "angle_windowsstore.h"
+#include <EGL/eglplatform.h>
+
+#include <windows.applicationmodel.core.h>
#include <windows.ui.xaml.h>
#include <windows.ui.xaml.media.dxinterop.h>
+#include <wrl.h>
+#include <wrl/wrappers/corewrappers.h>
using namespace Microsoft::WRL;
using namespace Microsoft::WRL::Wrappers;
@@ -26,7 +30,8 @@ using namespace ABI::Windows::Foundation::Collections;
namespace rx
{
-long ConvertDipsToPixels(float dips);
+float ConvertDipsToPixels(float dips);
+float GetLogicalDpi();
class InspectableNativeWindow
{
@@ -35,24 +40,25 @@ class InspectableNativeWindow
mSupportsSwapChainResize(true),
mSwapChainSizeSpecified(false),
mSwapChainScaleSpecified(false),
- mSwapChainScale(1.0f),
mClientRectChanged(false),
mClientRect({0,0,0,0}),
- mNewClientRect({0,0,0,0}),
- mRotationFlags(NativeWindow::RotateNone)
+ mNewClientRect({0,0,0,0})
{
mSizeChangedEventToken.value = 0;
+ mSwapChainScale = 96.0f / GetLogicalDpi();
+ if (mSwapChainScale != 1.0f)
+ mSwapChainScaleSpecified = true;
}
virtual ~InspectableNativeWindow(){}
virtual bool initialize(EGLNativeWindowType window, IPropertySet *propertySet) = 0;
virtual HRESULT createSwapChain(ID3D11Device *device,
- DXGIFactory *factory,
+ IDXGIFactory2 *factory,
DXGI_FORMAT format,
unsigned int width,
unsigned int height,
bool containsAlpha,
- DXGISwapChain **swapChain) = 0;
+ IDXGISwapChain1 **swapChain) = 0;
bool getClientRect(RECT *rect)
{
@@ -77,8 +83,7 @@ class InspectableNativeWindow
// If the swapchain size was specified then we should ignore this call too
if (!mSwapChainSizeSpecified)
{
- // We don't have to check if a swapchain scale was specified here; the default value is 1.0f which will have no effect.
- mNewClientRect = { 0, 0, ConvertDipsToPixels(newWindowSize.Width), ConvertDipsToPixels(newWindowSize.Height) };
+ mNewClientRect = clientRect(newWindowSize);
mClientRectChanged = true;
// If a scale was specified, then now is the time to apply the scale matrix for the new swapchain size and window size
@@ -97,18 +102,9 @@ class InspectableNativeWindow
}
}
- NativeWindow::RotationFlags rotationFlags() const
- {
- return mRotationFlags;
- }
-
- void setRotationFlags(NativeWindow::RotationFlags flags)
- {
- mRotationFlags = flags;
- }
-
protected:
virtual HRESULT scaleSwapChain(const Size &windowSize, const RECT &clientRect) = 0;
+ RECT clientRect(const Size &size);
bool mSupportsSwapChainResize; // Support for IDXGISwapChain::ResizeBuffers method
bool mSwapChainSizeSpecified; // If an EGLRenderSurfaceSizeProperty was specified
@@ -117,12 +113,10 @@ class InspectableNativeWindow
RECT mClientRect;
RECT mNewClientRect;
bool mClientRectChanged;
- NativeWindow::RotationFlags mRotationFlags;
EventRegistrationToken mSizeChangedEventToken;
};
-bool IsValidEGLNativeWindowType(EGLNativeWindowType window);
bool IsCoreWindow(EGLNativeWindowType window, ComPtr<ABI::Windows::UI::Core::ICoreWindow> *coreWindow = nullptr);
bool IsSwapChainPanel(EGLNativeWindowType window, ComPtr<ABI::Windows::UI::Xaml::Controls::ISwapChainPanel> *swapChainPanel = nullptr);
bool IsEGLConfiguredPropertySet(EGLNativeWindowType window, ABI::Windows::Foundation::Collections::IPropertySet **propertySet = nullptr, IInspectable **inspectable = nullptr);
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/NativeWindow11WinRT.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/NativeWindow11WinRT.cpp
new file mode 100644
index 0000000000..655b23be83
--- /dev/null
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/NativeWindow11WinRT.cpp
@@ -0,0 +1,126 @@
+//
+// Copyright (c) 2016 The ANGLE Project Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+//
+
+// NativeWindow11WinRT.cpp: NativeWindow base class for managing IInspectable native window types.
+
+#include "libANGLE/renderer/d3d/d3d11/winrt/NativeWindow11WinRT.h"
+
+#include "libANGLE/renderer/d3d/d3d11/renderer11_utils.h"
+#include "libANGLE/renderer/d3d/d3d11/winrt/CoreWindowNativeWindow.h"
+#include "libANGLE/renderer/d3d/d3d11/winrt/InspectableNativeWindow.h"
+#include "libANGLE/renderer/d3d/d3d11/winrt/SwapChainPanelNativeWindow.h"
+
+using namespace Microsoft::WRL;
+using namespace Microsoft::WRL::Wrappers;
+
+namespace rx
+{
+NativeWindow11WinRT::NativeWindow11WinRT(EGLNativeWindowType window, bool hasAlpha)
+ : NativeWindow11(window), mHasAlpha(hasAlpha)
+{
+}
+
+bool NativeWindow11WinRT::initialize()
+{
+ EGLNativeWindowType window = getNativeWindow();
+
+ // If the native window type is a IPropertySet, extract the
+ // EGLNativeWindowType (IInspectable) and initialize the
+ // proper host with this IPropertySet.
+ ComPtr<ABI::Windows::Foundation::Collections::IPropertySet> propertySet;
+ ComPtr<IInspectable> eglNativeWindow;
+ if (IsEGLConfiguredPropertySet(window, &propertySet, &eglNativeWindow))
+ {
+ // A property set was found and the EGLNativeWindowType was
+ // retrieved. The mWindow member of the host to must be updated
+ // to use the EGLNativeWindowType specified in the property set.
+ // mWindow is treated as a raw pointer not an AddRef'd interface, so
+ // the old mWindow does not need a Release() before this assignment.
+ window = eglNativeWindow.Get();
+ }
+
+ ComPtr<ABI::Windows::UI::Core::ICoreWindow> coreWindow;
+ ComPtr<ABI::Windows::UI::Xaml::Controls::ISwapChainPanel> swapChainPanel;
+ if (IsCoreWindow(window, &coreWindow))
+ {
+ mImpl = std::make_shared<CoreWindowNativeWindow>();
+ if (mImpl)
+ {
+ return mImpl->initialize(window, propertySet.Get());
+ }
+ }
+ else if (IsSwapChainPanel(window, &swapChainPanel))
+ {
+ mImpl = std::make_shared<SwapChainPanelNativeWindow>();
+ if (mImpl)
+ {
+ return mImpl->initialize(window, propertySet.Get());
+ }
+ }
+ else
+ {
+ ERR() << "Invalid IInspectable EGLNativeWindowType detected. Valid IInspectables include "
+ "ICoreWindow, ISwapChainPanel and IPropertySet";
+ }
+
+ return false;
+}
+
+bool NativeWindow11WinRT::getClientRect(LPRECT rect) const
+{
+ if (mImpl)
+ {
+ return mImpl->getClientRect(rect);
+ }
+
+ return false;
+}
+
+bool NativeWindow11WinRT::isIconic() const
+{
+ return false;
+}
+
+HRESULT NativeWindow11WinRT::createSwapChain(ID3D11Device *device,
+ IDXGIFactory *factory,
+ DXGI_FORMAT format,
+ UINT width,
+ UINT height,
+ UINT samples,
+ IDXGISwapChain **swapChain)
+{
+ if (mImpl)
+ {
+ IDXGIFactory2 *factory2 = d3d11::DynamicCastComObject<IDXGIFactory2>(factory);
+ IDXGISwapChain1 *swapChain1 = nullptr;
+ HRESULT result =
+ mImpl->createSwapChain(device, factory2, format, width, height, mHasAlpha, &swapChain1);
+ SafeRelease(factory2);
+ *swapChain = static_cast<IDXGISwapChain *>(swapChain1);
+ return result;
+ }
+
+ return E_UNEXPECTED;
+}
+
+void NativeWindow11WinRT::commitChange()
+{
+}
+
+// static
+bool NativeWindow11WinRT::IsValidNativeWindow(EGLNativeWindowType window)
+{
+ // A Valid EGLNativeWindowType IInspectable can only be:
+ //
+ // ICoreWindow
+ // ISwapChainPanel
+ // IPropertySet
+ //
+ // Anything else will be rejected as an invalid IInspectable.
+ return IsCoreWindow(window) || IsSwapChainPanel(window) || IsEGLConfiguredPropertySet(window);
+}
+
+} // namespace rx
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/NativeWindow11WinRT.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/NativeWindow11WinRT.h
new file mode 100644
index 0000000000..c4ac997a55
--- /dev/null
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/NativeWindow11WinRT.h
@@ -0,0 +1,51 @@
+//
+// Copyright (c) 2016 The ANGLE Project Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+//
+
+// NativeWindow11WinRT.h: NativeWindow base class for managing IInspectable native window types.
+
+#ifndef LIBANGLE_RENDERER_D3D_D3D11_WINRT_NATIVEWINDOW11WINRT_H_
+#define LIBANGLE_RENDERER_D3D_D3D11_WINRT_NATIVEWINDOW11WINRT_H_
+
+#include "libANGLE/renderer/d3d/d3d11/NativeWindow11.h"
+
+#include <memory>
+#include <windows.applicationmodel.core.h>
+#include <wrl.h>
+#include <wrl/wrappers/corewrappers.h>
+
+namespace rx
+{
+class InspectableNativeWindow;
+
+class NativeWindow11WinRT : public NativeWindow11
+{
+ public:
+ NativeWindow11WinRT(EGLNativeWindowType window, bool hasAlpha);
+
+ bool initialize() override;
+ bool getClientRect(LPRECT rect) const override;
+ bool isIconic() const override;
+
+ HRESULT createSwapChain(ID3D11Device *device,
+ IDXGIFactory *factory,
+ DXGI_FORMAT format,
+ UINT width,
+ UINT height,
+ UINT samples,
+ IDXGISwapChain **swapChain) override;
+
+ void commitChange() override;
+
+ static bool IsValidNativeWindow(EGLNativeWindowType window);
+
+ private:
+ bool mHasAlpha;
+ std::shared_ptr<InspectableNativeWindow> mImpl;
+};
+
+} // namespace rx
+
+#endif // LIBANGLE_RENDERER_D3D_D3D11_WINRT_NATIVEWINDOW11WINRT_H_
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/SwapChainPanelNativeWindow.cpp b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/SwapChainPanelNativeWindow.cpp
index 548b4602fd..3425fad95d 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/SwapChainPanelNativeWindow.cpp
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/SwapChainPanelNativeWindow.cpp
@@ -49,7 +49,8 @@ HRESULT RunOnUIThread(CODE &&code, const ComPtr<ICoreDispatcher> &dispatcher)
}
else
{
- Event waitEvent(CreateEventEx(NULL, NULL, CREATE_EVENT_MANUAL_RESET, EVENT_ALL_ACCESS));
+ Event waitEvent(
+ CreateEventEx(nullptr, nullptr, CREATE_EVENT_MANUAL_RESET, EVENT_ALL_ACCESS));
if (!waitEvent.IsValid())
{
return E_FAIL;
@@ -78,7 +79,8 @@ HRESULT RunOnUIThread(CODE &&code, const ComPtr<ICoreDispatcher> &dispatcher)
// unrecoverable state (probably deadlocked). We therefore terminate the application
// entirely. This also prevents stack corruption if the async operation is eventually
// run.
- ERR("Timeout waiting for async action on UI thread. The UI thread might be blocked.");
+ ERR()
+ << "Timeout waiting for async action on UI thread. The UI thread might be blocked.";
std::terminate();
return E_FAIL;
}
@@ -132,7 +134,8 @@ bool SwapChainPanelNativeWindow::initialize(EGLNativeWindowType window, IPropert
// A EGLRenderSurfaceSizeProperty and a EGLRenderResolutionScaleProperty can't both be specified
if (mSwapChainScaleSpecified && mSwapChainSizeSpecified)
{
- ERR("It is invalid to specify both an EGLRenderSurfaceSizeProperty and a EGLRenderResolutionScaleProperty.");
+ ERR() << "It is invalid to specify both an EGLRenderSurfaceSizeProperty and a "
+ "EGLRenderResolutionScaleProperty.";
return false;
}
}
@@ -169,17 +172,14 @@ bool SwapChainPanelNativeWindow::initialize(EGLNativeWindowType window, IPropert
}
else
{
- SIZE swapChainPanelSize;
+ Size swapChainPanelSize;
result = GetSwapChainPanelSize(mSwapChainPanel, mSwapChainPanelDispatcher,
- &swapChainPanelSize, &mSwapChainScale);
- if (mSwapChainScale != 1.0f)
- mSwapChainScaleSpecified = true;
+ &swapChainPanelSize);
if (SUCCEEDED(result))
{
// Update the client rect to account for any swapchain scale factor
- mClientRect = { 0, 0, static_cast<long>(ConvertDipsToPixels(swapChainPanelSize.cx * mSwapChainScale)),
- static_cast<long>(ConvertDipsToPixels(swapChainPanelSize.cy * mSwapChainScale)) };
+ mClientRect = clientRect(swapChainPanelSize);
}
}
}
@@ -241,14 +241,15 @@ void SwapChainPanelNativeWindow::unregisterForSizeChangeEvents()
}
HRESULT SwapChainPanelNativeWindow::createSwapChain(ID3D11Device *device,
- DXGIFactory *factory,
+ IDXGIFactory2 *factory,
DXGI_FORMAT format,
unsigned int width,
unsigned int height,
bool containsAlpha,
- DXGISwapChain **swapChain)
+ IDXGISwapChain1 **swapChain)
{
- if (device == NULL || factory == NULL || swapChain == NULL || width == 0 || height == 0)
+ if (device == nullptr || factory == nullptr || swapChain == nullptr || width == 0 ||
+ height == 0)
{
return E_INVALIDARG;
}
@@ -272,6 +273,7 @@ HRESULT SwapChainPanelNativeWindow::createSwapChain(ID3D11Device *device,
ComPtr<IDXGISwapChain1> newSwapChain;
ComPtr<ISwapChainPanelNative> swapChainPanelNative;
+ Size currentPanelSize = {};
HRESULT result = factory->CreateSwapChainForComposition(device, &swapChainDesc, nullptr, newSwapChain.ReleaseAndGetAddressOf());
@@ -306,14 +308,14 @@ HRESULT SwapChainPanelNativeWindow::createSwapChain(ID3D11Device *device,
{
if (mSwapChainSizeSpecified || mSwapChainScaleSpecified)
{
- ComPtr<ABI::Windows::UI::Xaml::IUIElement> uiElement;
- result = mSwapChainPanel.As(&uiElement);
- ASSERT(SUCCEEDED(result));
-
- Size currentSize;
- result = uiElement->get_RenderSize(&currentSize);
- ASSERT(SUCCEEDED(result));
- result = scaleSwapChain(currentSize, mClientRect);
+ result = GetSwapChainPanelSize(mSwapChainPanel, mSwapChainPanelDispatcher,
+ &currentPanelSize);
+
+ // Scale the swapchain to fit inside the contents of the panel.
+ if (SUCCEEDED(result))
+ {
+ result = scaleSwapChain(currentPanelSize, mClientRect);
+ }
}
}
@@ -342,31 +344,14 @@ HRESULT SwapChainPanelNativeWindow::scaleSwapChain(const Size &windowSize, const
HRESULT GetSwapChainPanelSize(
const ComPtr<ABI::Windows::UI::Xaml::Controls::ISwapChainPanel> &swapChainPanel,
const ComPtr<ICoreDispatcher> &dispatcher,
- SIZE *windowSize, float *scaleFactor)
+ Size *windowSize)
{
ComPtr<IUIElement> uiElement;
- Size renderSize = {0, 0};
HRESULT result = swapChainPanel.As(&uiElement);
if (SUCCEEDED(result))
{
result = RunOnUIThread(
- [uiElement, &renderSize]
- {
- return uiElement->get_RenderSize(&renderSize);
- },
- dispatcher);
- }
-
- if (SUCCEEDED(result))
- {
- long width = ConvertDipsToPixels(renderSize.Width);
- long height = ConvertDipsToPixels(renderSize.Height);
- *windowSize = { width, height };
-
- if (scaleFactor)
- {
- *scaleFactor = renderSize.Width / width;
- }
+ [uiElement, windowSize] { return uiElement->get_RenderSize(windowSize); }, dispatcher);
}
return result;
diff --git a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/SwapChainPanelNativeWindow.h b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/SwapChainPanelNativeWindow.h
index 09d87ad523..f9a2fc0e4b 100644
--- a/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/SwapChainPanelNativeWindow.h
+++ b/src/3rdparty/angle/src/libANGLE/renderer/d3d/d3d11/winrt/SwapChainPanelNativeWindow.h
@@ -11,6 +11,8 @@
#include "libANGLE/renderer/d3d/d3d11/winrt/InspectableNativeWindow.h"
+#include <memory>
+
namespace rx
{
class SwapChainPanelNativeWindow : public InspectableNativeWindow, public std::enable_shared_from_this<SwapChainPanelNativeWindow>
@@ -20,12 +22,12 @@ class SwapChainPanelNativeWindow : public InspectableNativeWindow, public std::e
bool initialize(EGLNativeWindowType window, IPropertySet *propertySet) override;
HRESULT createSwapChain(ID3D11Device *device,
- DXGIFactory *factory,
+ IDXGIFactory2 *factory,
DXGI_FORMAT format,
unsigned int width,
unsigned int height,
bool containsAlpha,
- DXGISwapChain **swapChain) override;
+ IDXGISwapChain1 **swapChain) override;
protected:
HRESULT scaleSwapChain(const Size &windowSize, const RECT &clientRect) override;
@@ -37,7 +39,7 @@ class SwapChainPanelNativeWindow : public InspectableNativeWindow, public std::e
ComPtr<ABI::Windows::UI::Xaml::Controls::ISwapChainPanel> mSwapChainPanel;
ComPtr<ABI::Windows::UI::Core::ICoreDispatcher> mSwapChainPanelDispatcher;
ComPtr<IMap<HSTRING, IInspectable*>> mPropertyMap;
- ComPtr<DXGISwapChain> mSwapChain;
+ ComPtr<IDXGISwapChain1> mSwapChain;
};
[uuid(8ACBD974-8187-4508-AD80-AEC77F93CF36)]
@@ -86,6 +88,6 @@ class SwapChainPanelSizeChangedHandler :
HRESULT GetSwapChainPanelSize(
const ComPtr<ABI::Windows::UI::Xaml::Controls::ISwapChainPanel> &swapChainPanel,
const ComPtr<ABI::Windows::UI::Core::ICoreDispatcher> &dispatcher,
- SIZE *windowSize, float *scaleFactor);
+ Size *windowSize);
}
#endif // LIBANGLE_RENDERER_D3D_D3D11_WINRT_SWAPCHAINPANELNATIVEWINDOW_H_