mirror of
https://github.com/doitsujin/dxvk.git
synced 2025-02-27 04:54:15 +01:00
Merge branch 'master' into filter-uuid
This commit is contained in:
commit
8e117058f0
17
.github/ISSUE_TEMPLATE/bug_report.md
vendored
17
.github/ISSUE_TEMPLATE/bug_report.md
vendored
@ -7,14 +7,9 @@ assignees: ''
|
||||
|
||||
---
|
||||
|
||||
Please describe your issue as accurately as possible. If you run into a problem with a binary release, make sure to test with latest `master` as well.
|
||||
Please describe your issue as accurately as possible.
|
||||
|
||||
**Important:** When reporting an issue with a specific game or application, such as crashes or rendering issues, please include log files and, if possible, a D3D11/D3D9 Apitrace (see https://github.com/apitrace/apitrace) so that the issue can be reproduced.
|
||||
In order to create a trace for **D3D11/D3D10**: Run `wine apitrace.exe trace -a dxgi YOURGAME.exe`.
|
||||
In order to create a trace for **D3D9**: Follow https://github.com/doitsujin/dxvk/wiki/Making-a-Trace.
|
||||
Preferably record the trace on Windows, or wined3d if possible.
|
||||
|
||||
**Reports with no log files will be ignored.**
|
||||
If you use Windows, please check the following page: https://github.com/doitsujin/dxvk/wiki/Windows
|
||||
|
||||
### Software information
|
||||
Name of the game, settings used etc.
|
||||
@ -28,7 +23,9 @@ Name of the game, settings used etc.
|
||||
### Apitrace file(s)
|
||||
- Put a link here
|
||||
|
||||
For instructions on how to use apitrace, see: https://github.com/doitsujin/dxvk/wiki/Using-Apitrace
|
||||
|
||||
### Log files
|
||||
- d3d9.log:
|
||||
- d3d11.log:
|
||||
- dxgi.log:
|
||||
Please attach Proton or Wine logs as a text file:
|
||||
- When using Proton, set the Steam launch options for your game to `PROTON_LOG=1 %command%` and attach the corresponding `steam-xxxxx.log` file in your home directory.
|
||||
- When using regular Wine, use `wine game.exe > game.log 2>&1` and attach the resulting `game.log` file.
|
41
.github/workflows/artifacts.yml
vendored
41
.github/workflows/artifacts.yml
vendored
@ -3,23 +3,23 @@ name: Artifacts (Package)
|
||||
on: [push, pull_request, workflow_dispatch]
|
||||
|
||||
jobs:
|
||||
build-artifacts:
|
||||
artifacts-mingw-w64:
|
||||
runs-on: ubuntu-20.04
|
||||
|
||||
steps:
|
||||
- name: Checkout code
|
||||
id: checkout-code
|
||||
uses: actions/checkout@v2
|
||||
uses: actions/checkout@v3
|
||||
with:
|
||||
submodules: recursive
|
||||
fetch-depth: 0
|
||||
|
||||
- name: Setup problem matcher
|
||||
uses: Joshua-Ashton/gcc-problem-matcher@v1
|
||||
uses: Joshua-Ashton/gcc-problem-matcher@v2
|
||||
|
||||
- name: Build release
|
||||
id: build-release
|
||||
uses: Joshua-Ashton/arch-mingw-github-action@v7
|
||||
uses: Joshua-Ashton/arch-mingw-github-action@v8
|
||||
with:
|
||||
command: |
|
||||
export VERSION_NAME="${GITHUB_REF##*/}-${GITHUB_SHA##*/}"
|
||||
@ -28,8 +28,39 @@ jobs:
|
||||
|
||||
- name: Upload artifacts
|
||||
id: upload-artifacts
|
||||
uses: actions/upload-artifact@v2
|
||||
uses: actions/upload-artifact@v3
|
||||
with:
|
||||
name: dxvk-${{ env.VERSION_NAME }}
|
||||
path: build/dxvk-${{ env.VERSION_NAME }}
|
||||
if-no-files-found: error
|
||||
|
||||
artifacts-steamrt-sniper:
|
||||
runs-on: ubuntu-20.04
|
||||
container: registry.gitlab.steamos.cloud/steamrt/sniper/sdk:beta
|
||||
|
||||
steps:
|
||||
- name: Checkout code
|
||||
id: checkout-code
|
||||
uses: actions/checkout@v3
|
||||
with:
|
||||
submodules: recursive
|
||||
fetch-depth: 0
|
||||
|
||||
- name: Setup problem matcher
|
||||
uses: Joshua-Ashton/gcc-problem-matcher@v2
|
||||
|
||||
- name: Build release
|
||||
id: build-release
|
||||
shell: bash
|
||||
run: |
|
||||
export VERSION_NAME="${GITHUB_REF##*/}-${GITHUB_SHA##*/}"
|
||||
./package-native.sh ${VERSION_NAME} build --no-package
|
||||
echo "VERSION_NAME=${VERSION_NAME}" >> $GITHUB_ENV
|
||||
|
||||
- name: Upload artifacts
|
||||
id: upload-artifacts
|
||||
uses: actions/upload-artifact@v3
|
||||
with:
|
||||
name: dxvk-${{ env.VERSION_NAME }}
|
||||
path: build/dxvk-native-${{ env.VERSION_NAME }}
|
||||
if-no-files-found: error
|
||||
|
7
.github/workflows/test-build-windows.yml
vendored
7
.github/workflows/test-build-windows.yml
vendored
@ -9,16 +9,15 @@ jobs:
|
||||
steps:
|
||||
- name: Checkout code
|
||||
id: checkout-code
|
||||
uses: actions/checkout@v2
|
||||
uses: actions/checkout@v3
|
||||
with:
|
||||
submodules: recursive
|
||||
|
||||
- name: Setup glslangValidator
|
||||
shell: pwsh
|
||||
run: |
|
||||
choco install vulkan-sdk -y
|
||||
Write-Output "$([System.Environment]::GetEnvironmentVariable('VULKAN_SDK', 'Machine'))\Bin" `
|
||||
| Out-File -FilePath "${Env:GITHUB_PATH}" -Append
|
||||
Invoke-WebRequest -Uri "https://raw.githubusercontent.com/HansKristian-Work/vkd3d-proton-ci/main/glslangValidator.exe" -OutFile "glslangValidator.exe"
|
||||
Write-Output "$pwd" | Out-File -FilePath "${Env:GITHUB_PATH}" -Append
|
||||
|
||||
- name: Setup Meson
|
||||
shell: pwsh
|
||||
|
13
.gitmodules
vendored
Normal file
13
.gitmodules
vendored
Normal file
@ -0,0 +1,13 @@
|
||||
[submodule "include/native/directx"]
|
||||
path = include/native/directx
|
||||
url = https://github.com/Joshua-Ashton/mingw-directx-headers
|
||||
[submodule "include/vulkan"]
|
||||
path = include/vulkan
|
||||
url = https://github.com/KhronosGroup/Vulkan-Headers
|
||||
[submodule "include/spirv"]
|
||||
path = include/spirv
|
||||
url = https://github.com/KhronosGroup/SPIRV-Headers.git
|
||||
[submodule "subprojects/libdisplay-info"]
|
||||
path = subprojects/libdisplay-info
|
||||
url = https://gitlab.freedesktop.org/JoshuaAshton/libdisplay-info.git
|
||||
branch = windows
|
4
LICENSE
4
LICENSE
@ -1,5 +1,5 @@
|
||||
Copyright (c) 2017-2021 Philip Rebohle
|
||||
Copyright (c) 2019-2021 Joshua Ashton
|
||||
Copyright (c) 2017 Philip Rebohle
|
||||
Copyright (c) 2019 Joshua Ashton
|
||||
|
||||
zlib/libpng license
|
||||
|
||||
|
77
README.md
77
README.md
@ -9,34 +9,45 @@ The most recent development builds can be found [here](https://github.com/doitsu
|
||||
Release builds can be found [here](https://github.com/doitsujin/dxvk/releases).
|
||||
|
||||
## How to use
|
||||
In order to install a DXVK package obtained from the [release](https://github.com/doitsujin/dxvk/releases) page into a given wine prefix, run the following commands from within the DXVK directory:
|
||||
In order to install a DXVK package obtained from the [release](https://github.com/doitsujin/dxvk/releases) page into a given wine prefix, copy or symlink the DLLs into the following directories as follows, then open `winecfg` and manually add DLL overrides for `d3d11`, `d3d10core`, `dxgi`, and `d3d9`.
|
||||
|
||||
In a default Wine prefix that would be as follows:
|
||||
```
|
||||
export WINEPREFIX=/path/to/.wine-prefix
|
||||
./setup_dxvk.sh install
|
||||
export WINEPREFIX=/path/to/wineprefix
|
||||
cp x64/*.dll $WINEPREFIX/drive_c/windows/system32
|
||||
cp x32/*.dll $WINEPREFIX/drive_c/windows/syswow64
|
||||
winecfg
|
||||
```
|
||||
|
||||
This will **copy** the DLLs into the `system32` and `syswow64` directories of your wine prefix and set up the required DLL overrides. Pure 32-bit prefixes are also supported.
|
||||
|
||||
The setup script optionally takes the following arguments:
|
||||
- `--symlink`: Create symbolic links to the DLL files instead of copying them. This is especially useful for development.
|
||||
- `--with-d3d10`: Install the `d3d10{_1}.dll` helper libraries.
|
||||
- `--without-dxgi`: Do not install DXVK's DXGI implementation and use the one provided by wine instead.
|
||||
|
||||
Verify that your application uses DXVK instead of wined3d by checking for the presence of the log file `d3d9.log` or `d3d11.log` in the application's directory, or by enabling the HUD (see notes below).
|
||||
|
||||
In order to remove DXVK from a prefix, run the following command:
|
||||
For a pure 32-bit Wine prefix (non default) the 32-bit DLLs instead go to the `system32` directory:
|
||||
```
|
||||
export WINEPREFIX=/path/to/.wine-prefix
|
||||
./setup_dxvk.sh uninstall
|
||||
export WINEPREFIX=/path/to/wineprefix
|
||||
cp x32/*.dll $WINEPREFIX/drive_c/windows/system32
|
||||
winecfg
|
||||
```
|
||||
|
||||
Verify that your application uses DXVK instead of wined3d by enabling the HUD (see notes below).
|
||||
|
||||
In order to remove DXVK from a prefix, remove the DLLs and DLL overrides, and run `wineboot -u` to restore the original DLL files.
|
||||
|
||||
Tools such as Steam Play, Lutris, Bottles, Heroic Launcher, etc will automatically handle setup of dxvk on their own when enabled.
|
||||
|
||||
### Notes on Vulkan drivers
|
||||
Before reporting an issue, please check the [Wiki](https://github.com/doitsujin/dxvk/wiki/Driver-support) page on the current driver status and make sure you run a recent enough driver version for your hardware.
|
||||
|
||||
## Build instructions
|
||||
|
||||
In order to pull in all submodules that are needed for building, clone the repository using the following command:
|
||||
```
|
||||
git clone --recursive https://github.com/doitsujin/dxvk.git
|
||||
```
|
||||
|
||||
|
||||
|
||||
### Requirements:
|
||||
- [wine 3.10](https://www.winehq.org/) or newer
|
||||
- [Meson](https://mesonbuild.com/) build system (at least version 0.46)
|
||||
- [Mingw-w64](https://www.mingw-w64.org) compiler and headers (at least version 8.0)
|
||||
- [wine 7.1](https://www.winehq.org/) or newer
|
||||
- [Meson](https://mesonbuild.com/) build system (at least version 0.49)
|
||||
- [Mingw-w64](https://www.mingw-w64.org) compiler and headers (at least version 10.0)
|
||||
- [glslang](https://github.com/KhronosGroup/glslang) compiler
|
||||
|
||||
### Building DLLs
|
||||
@ -60,19 +71,21 @@ ninja install
|
||||
```
|
||||
# 64-bit build. For 32-bit builds, replace
|
||||
# build-win64.txt with build-win32.txt
|
||||
meson --cross-file build-win64.txt --buildtype release --prefix /your/dxvk/directory build.w64
|
||||
meson setup --cross-file build-win64.txt --buildtype release --prefix /your/dxvk/directory build.w64
|
||||
cd build.w64
|
||||
ninja install
|
||||
```
|
||||
|
||||
The D3D9, D3D10, D3D11 and DXGI DLLs will be located in `/your/dxvk/directory/bin`. Setup has to be done manually in this case.
|
||||
|
||||
### Notes on Vulkan drivers
|
||||
Before reporting an issue, please check the [Wiki](https://github.com/doitsujin/dxvk/wiki/Driver-support) page on the current driver status and make sure you run a recent enough driver version for your hardware.
|
||||
|
||||
### Online multi-player games
|
||||
Manipulation of Direct3D libraries in multi-player games may be considered cheating and can get your account **banned**. This may also apply to single-player games with an embedded or dedicated multiplayer portion. **Use at your own risk.**
|
||||
|
||||
### Logs
|
||||
When used with Wine, DXVK will print log messages to `stderr`. Additionally, standalone log files can optionally be generated by setting the `DXVK_LOG_PATH` variable, where log files in the given directory will be called `app_d3d11.log`, `app_dxgi.log` etc., where `app` is the name of the game executable.
|
||||
|
||||
On Windows, log files will be created in the game's working directory by default, which is usually next to the game executable.
|
||||
|
||||
### HUD
|
||||
The `DXVK_HUD` environment variable controls a HUD which can display the framerate and some stat counters. It accepts a comma-separated list of the following options:
|
||||
- `devinfo`: Displays the name of the GPU and the driver version.
|
||||
@ -81,6 +94,7 @@ The `DXVK_HUD` environment variable controls a HUD which can display the framera
|
||||
- `submissions`: Shows the number of command buffers submitted per frame.
|
||||
- `drawcalls`: Shows the number of draw calls and render passes per frame.
|
||||
- `pipelines`: Shows the total number of graphics and compute pipelines.
|
||||
- `descriptors`: Shows the number of descriptor pools and descriptor sets.
|
||||
- `memory`: Shows the amount of device memory allocated and used.
|
||||
- `gpuload`: Shows estimated GPU load. May be inaccurate.
|
||||
- `version`: Shows DXVK version.
|
||||
@ -89,6 +103,7 @@ The `DXVK_HUD` environment variable controls a HUD which can display the framera
|
||||
- `compiler`: Shows shader compiler activity
|
||||
- `samplers`: Shows the current number of sampler pairs used *[D3D9 Only]*
|
||||
- `scale=x`: Scales the HUD by a factor of `x` (e.g. `1.5`)
|
||||
- `opacity=y`: Adjusts the HUD opacity by a factor of `y` (e.g. `0.5`, `1.0` being fully opaque).
|
||||
|
||||
Additionally, `DXVK_HUD=1` has the same effect as `DXVK_HUD=devinfo,fps`, and `DXVK_HUD=full` enables all available HUD elements.
|
||||
|
||||
@ -101,20 +116,34 @@ Some applications do not provide a method to select a different GPU. In that cas
|
||||
|
||||
**Note:** If the device filter is configured incorrectly, it may filter out all devices and applications will be unable to create a D3D device.
|
||||
|
||||
### Graphics Pipeline Library
|
||||
On drivers which support `VK_EXT_graphics_pipeline_library` Vulkan shaders will be compiled at the time the game loads its D3D shaders, rather than at draw time. This reduces or eliminates shader compile stutter in many games when compared to the previous system.
|
||||
|
||||
In games that load their shaders during loading screens or in the menu, this can lead to prolonged periods of very high CPU utilization, especially on weaker CPUs. For affected games it is recommended to wait for shader compilation to finish before starting the game to avoid stutter and low performance. Shader compiler activity can be monitored with `DXVK_HUD=compiler`.
|
||||
|
||||
This feature largely replaces the state cache.
|
||||
|
||||
**Note:** Games which only load their D3D shaders at draw time (e.g. most Unreal Engine games) will still exhibit some stutter, although it should still be less severe than without this feature.
|
||||
|
||||
### State cache
|
||||
DXVK caches pipeline state by default, so that shaders can be recompiled ahead of time on subsequent runs of an application, even if the driver's own shader cache got invalidated in the meantime. This cache is enabled by default, and generally reduces stuttering.
|
||||
|
||||
The following environment variables can be used to control the cache:
|
||||
- `DXVK_STATE_CACHE=0` Disables the state cache.
|
||||
- `DXVK_STATE_CACHE`: Controls the state cache. The following values are supported:
|
||||
- `disable`: Disables the cache entirely.
|
||||
- `reset`: Clears the cache file.
|
||||
- `DXVK_STATE_CACHE_PATH=/some/directory` Specifies a directory where to put the cache files. Defaults to the current working directory of the application.
|
||||
|
||||
This feature is mostly only relevant on systems without support for `VK_EXT_graphics_pipeline_library`
|
||||
|
||||
### Debugging
|
||||
The following environment variables can be used for **debugging** purposes.
|
||||
- `VK_INSTANCE_LAYERS=VK_LAYER_KHRONOS_validation` Enables Vulkan debug layers. Highly recommended for troubleshooting rendering issues and driver crashes. Requires the Vulkan SDK to be installed on the host system.
|
||||
- `DXVK_LOG_LEVEL=none|error|warn|info|debug` Controls message logging.
|
||||
- `DXVK_LOG_PATH=/some/directory` Changes path where log files are stored. Set to `none` to disable log file creation entirely, without disabling logging.
|
||||
- `DXVK_DEBUG=markers|validation` Enables use of the `VK_EXT_debug_utils` extension for translating performance event markers, or to enable Vulkan validation, respecticely.
|
||||
- `DXVK_CONFIG_FILE=/xxx/dxvk.conf` Sets path to the configuration file.
|
||||
- `DXVK_PERF_EVENTS=1` Enables use of the VK_EXT_debug_utils extension for translating performance event markers.
|
||||
- `DXVK_CONFIG="dxgi.hideAmdGpu = True; dxgi.syncInterval = 0"` Can be used to set config variables through the environment instead of a configuration file using the same syntax. `;` is used as a seperator.
|
||||
|
||||
## Troubleshooting
|
||||
DXVK requires threading support from your mingw-w64 build environment. If you
|
||||
|
415
VP_DXVK_requirements.json
Normal file
415
VP_DXVK_requirements.json
Normal file
@ -0,0 +1,415 @@
|
||||
{
|
||||
"$schema": "https://schema.khronos.org/vulkan/profiles-0.8.1-224.json#",
|
||||
"capabilities": {
|
||||
"vulkan10requirements": {
|
||||
"features": {
|
||||
"VkPhysicalDeviceFeatures": {
|
||||
"robustBufferAccess": true
|
||||
}
|
||||
}
|
||||
},
|
||||
"vulkan11requirements": {
|
||||
"features": {
|
||||
"VkPhysicalDeviceVulkan11Features": {
|
||||
"multiview": true
|
||||
}
|
||||
},
|
||||
"properties": {
|
||||
"VkPhysicalDeviceVulkan11Properties": {
|
||||
"maxMultiviewViewCount": 6,
|
||||
"maxMultiviewInstanceIndex": 134217727
|
||||
}
|
||||
}
|
||||
},
|
||||
"vulkan12requirements": {
|
||||
"features": {
|
||||
"VkPhysicalDeviceVulkan12Features": {
|
||||
"uniformBufferStandardLayout": true,
|
||||
"subgroupBroadcastDynamicId": true,
|
||||
"imagelessFramebuffer": true,
|
||||
"separateDepthStencilLayouts": true,
|
||||
"hostQueryReset": true,
|
||||
"timelineSemaphore": true,
|
||||
"shaderSubgroupExtendedTypes": true
|
||||
}
|
||||
},
|
||||
"properties": {
|
||||
"VkPhysicalDeviceVulkan12Properties": {
|
||||
"maxTimelineSemaphoreValueDifference": 2147483647
|
||||
}
|
||||
}
|
||||
},
|
||||
"vulkan13requirements": {
|
||||
"features": {
|
||||
"VkPhysicalDeviceVulkan12Features": {
|
||||
"vulkanMemoryModel": true,
|
||||
"vulkanMemoryModelDeviceScope": true,
|
||||
"bufferDeviceAddress": true
|
||||
},
|
||||
"VkPhysicalDeviceVulkan13Features": {
|
||||
"robustImageAccess": true,
|
||||
"shaderTerminateInvocation": true,
|
||||
"shaderZeroInitializeWorkgroupMemory": true,
|
||||
"synchronization2": true,
|
||||
"shaderIntegerDotProduct": true,
|
||||
"maintenance4": true,
|
||||
"pipelineCreationCacheControl": true,
|
||||
"subgroupSizeControl": true,
|
||||
"computeFullSubgroups": true,
|
||||
"shaderDemoteToHelperInvocation": true,
|
||||
"inlineUniformBlock": true,
|
||||
"dynamicRendering": true
|
||||
}
|
||||
},
|
||||
"properties": {
|
||||
"VkPhysicalDeviceVulkan13Properties": {
|
||||
"maxBufferSize": 1073741824,
|
||||
"maxInlineUniformBlockSize": 256,
|
||||
"maxPerStageDescriptorInlineUniformBlocks": 4,
|
||||
"maxPerStageDescriptorUpdateAfterBindInlineUniformBlocks": 4,
|
||||
"maxDescriptorSetInlineUniformBlocks": 4,
|
||||
"maxDescriptorSetUpdateAfterBindInlineUniformBlocks": 4,
|
||||
"maxInlineUniformTotalSize": 4
|
||||
}
|
||||
}
|
||||
},
|
||||
"d3d9_baseline": {
|
||||
"extensions": {
|
||||
"VK_EXT_robustness2": 1
|
||||
},
|
||||
"features": {
|
||||
"VkPhysicalDeviceFeatures": {
|
||||
"geometryShader": true,
|
||||
"imageCubeArray": true,
|
||||
"depthClamp": true,
|
||||
"depthBiasClamp": true,
|
||||
"fillModeNonSolid": true,
|
||||
"sampleRateShading": true,
|
||||
"shaderClipDistance": true,
|
||||
"shaderCullDistance": true,
|
||||
"textureCompressionBC": true,
|
||||
"occlusionQueryPrecise": true,
|
||||
"independentBlend": true,
|
||||
"fullDrawIndexUint32": true,
|
||||
|
||||
"shaderImageGatherExtended": true
|
||||
},
|
||||
"VkPhysicalDeviceVulkan12Features": {
|
||||
"samplerMirrorClampToEdge": true
|
||||
},
|
||||
"VkPhysicalDeviceRobustness2FeaturesEXT": {
|
||||
"nullDescriptor": true,
|
||||
"robustBufferAccess2": true
|
||||
}
|
||||
}
|
||||
},
|
||||
"d3d9_optional": {
|
||||
"extensions": {
|
||||
"VK_EXT_memory_priority": 1,
|
||||
"VK_EXT_vertex_attribute_divisor": 1,
|
||||
"VK_EXT_depth_clip_enable": 1,
|
||||
"VK_EXT_custom_border_color": 1,
|
||||
"VK_EXT_attachment_feedback_loop_layout": 1,
|
||||
"VK_EXT_non_seamless_cube_map": 1
|
||||
},
|
||||
"features": {
|
||||
"VkPhysicalDeviceFeatures": {
|
||||
"depthBounds": true,
|
||||
"vertexPipelineStoresAndAtomics": true,
|
||||
"pipelineStatisticsQuery": true,
|
||||
"samplerAnisotropy": true
|
||||
},
|
||||
"VkPhysicalDeviceMemoryPriorityFeaturesEXT": {
|
||||
"memoryPriority": true
|
||||
},
|
||||
"VkPhysicalDeviceVertexAttributeDivisorFeaturesEXT": {
|
||||
"vertexAttributeInstanceRateDivisor": true,
|
||||
"vertexAttributeInstanceRateZeroDivisor": true
|
||||
},
|
||||
"VkPhysicalDeviceDepthClipEnableFeaturesEXT": {
|
||||
"depthClipEnable": true
|
||||
},
|
||||
"VkPhysicalDeviceCustomBorderColorFeaturesEXT": {
|
||||
"customBorderColors": true,
|
||||
"customBorderColorWithoutFormat": true
|
||||
},
|
||||
"VkPhysicalDeviceAttachmentFeedbackLoopLayoutFeaturesEXT": {
|
||||
"attachmentFeedbackLoopLayout": true
|
||||
},
|
||||
"VkPhysicalDeviceNonSeamlessCubeMapFeaturesEXT": {
|
||||
"nonSeamlessCubeMap": true
|
||||
}
|
||||
}
|
||||
},
|
||||
"d3d11_baseline": {
|
||||
"extensions": {
|
||||
"VK_EXT_robustness2": 1,
|
||||
"VK_EXT_transform_feedback": 1
|
||||
},
|
||||
"features": {
|
||||
"VkPhysicalDeviceFeatures": {
|
||||
"depthBiasClamp": true,
|
||||
"depthClamp": true,
|
||||
"dualSrcBlend": true,
|
||||
"fillModeNonSolid": true,
|
||||
"fullDrawIndexUint32": true,
|
||||
"geometryShader": true,
|
||||
"imageCubeArray": true,
|
||||
"independentBlend": true,
|
||||
"multiViewport": true,
|
||||
"occlusionQueryPrecise": true,
|
||||
"sampleRateShading": true,
|
||||
"shaderClipDistance": true,
|
||||
"shaderCullDistance": true,
|
||||
"shaderImageGatherExtended": true,
|
||||
"textureCompressionBC": true
|
||||
},
|
||||
"VkPhysicalDeviceVulkan11Features": {
|
||||
"shaderDrawParameters": true
|
||||
},
|
||||
"VkPhysicalDeviceVulkan12Features": {
|
||||
"samplerMirrorClampToEdge": true
|
||||
},
|
||||
"VkPhysicalDeviceRobustness2FeaturesEXT": {
|
||||
"nullDescriptor": true,
|
||||
"robustBufferAccess2": true
|
||||
},
|
||||
"VkPhysicalDeviceTransformFeedbackFeaturesEXT": {
|
||||
"transformFeedback": true,
|
||||
"geometryStreams": true
|
||||
}
|
||||
}
|
||||
},
|
||||
"d3d11_baseline_optional":{
|
||||
"extensions": {
|
||||
"VK_EXT_memory_priority": 1,
|
||||
"VK_EXT_vertex_attribute_divisor": 1,
|
||||
"VK_EXT_custom_border_color": 1,
|
||||
"VK_EXT_depth_clip_enable": 1,
|
||||
"VK_EXT_swapchain_colorspace": 1,
|
||||
"VK_EXT_hdr_metadata": 1
|
||||
},
|
||||
"features": {
|
||||
"VkPhysicalDeviceFeatures": {
|
||||
"depthBounds": true,
|
||||
"pipelineStatisticsQuery": true,
|
||||
"logicOp": true,
|
||||
"samplerAnisotropy": true
|
||||
},
|
||||
"VkPhysicalDeviceMemoryPriorityFeaturesEXT": {
|
||||
"memoryPriority": true
|
||||
},
|
||||
"VkPhysicalDeviceVertexAttributeDivisorFeaturesEXT": {
|
||||
"vertexAttributeInstanceRateDivisor": true,
|
||||
"vertexAttributeInstanceRateZeroDivisor": true
|
||||
},
|
||||
"VkPhysicalDeviceCustomBorderColorFeaturesEXT": {
|
||||
"customBorderColors": true,
|
||||
"customBorderColorWithoutFormat": true
|
||||
},
|
||||
"VkPhysicalDeviceDepthClipEnableFeaturesEXT": {
|
||||
"depthClipEnable": true
|
||||
}
|
||||
}
|
||||
},
|
||||
"d3d11_level11_0": {
|
||||
"features": {
|
||||
"VkPhysicalDeviceFeatures": {
|
||||
"drawIndirectFirstInstance": true,
|
||||
"fragmentStoresAndAtomics": true,
|
||||
"multiDrawIndirect": true,
|
||||
"tessellationShader": true
|
||||
}
|
||||
}
|
||||
},
|
||||
"d3d11_level11_0_optional": {
|
||||
"features": {
|
||||
"VkPhysicalDeviceFeatures": {
|
||||
"shaderFloat64": true,
|
||||
"shaderInt64": true
|
||||
}
|
||||
}
|
||||
},
|
||||
"d3d11_level11_1": {
|
||||
"features": {
|
||||
"VkPhysicalDeviceFeatures": {
|
||||
"logicOp": true,
|
||||
"vertexPipelineStoresAndAtomics": true
|
||||
}
|
||||
}
|
||||
},
|
||||
"d3d11_level12_0": {
|
||||
"features": {
|
||||
"VkPhysicalDeviceFeatures": {
|
||||
"shaderResourceResidency": true,
|
||||
"shaderResourceMinLod": true,
|
||||
"sparseBinding": true,
|
||||
"sparseResidencyBuffer": true,
|
||||
"sparseResidencyAliased": true,
|
||||
"sparseResidencyImage2D": true
|
||||
},
|
||||
"VkPhysicalDeviceVulkan12Features": {
|
||||
"samplerFilterMinmax": true
|
||||
}
|
||||
},
|
||||
"properties": {
|
||||
"VkPhysicalDeviceProperties": {
|
||||
"sparseProperties": {
|
||||
"residencyStandard2DBlockShape": true,
|
||||
"residencyAlignedMipSize": false,
|
||||
"residencyNonResidentStrict": true
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
"profiles": {
|
||||
"VP_DXVK_d3d9_baseline": {
|
||||
"version": 1,
|
||||
"api-version": "1.3.204",
|
||||
"label": "DXVK D3D9 Baseline profile",
|
||||
"description": "DXVK for D3D9 minimum requirements",
|
||||
"capabilities": [
|
||||
"vulkan10requirements",
|
||||
"vulkan11requirements",
|
||||
"vulkan12requirements",
|
||||
"vulkan13requirements",
|
||||
"d3d9_baseline"
|
||||
]
|
||||
},
|
||||
"VP_DXVK_d3d9_optimal": {
|
||||
"version": 1,
|
||||
"api-version": "1.3.224",
|
||||
"label": "DXVK D3D9 Optimal profile",
|
||||
"description": "DXVK for D3D9 including optional capabilities",
|
||||
"capabilities": [
|
||||
"vulkan10requirements",
|
||||
"vulkan11requirements",
|
||||
"vulkan12requirements",
|
||||
"vulkan13requirements",
|
||||
"d3d9_baseline",
|
||||
"d3d9_optional"
|
||||
]
|
||||
},
|
||||
"VP_DXVK_d3d10_level_10_1_baseline": {
|
||||
"version": 1,
|
||||
"api-version": "1.3.204",
|
||||
"label": "DXVK D3D10 Level 10.1 Baseline profile",
|
||||
"description": "DXVK for D3D10 Feature Level 10.1 minimum requirements",
|
||||
"capabilities": [
|
||||
"vulkan10requirements",
|
||||
"vulkan11requirements",
|
||||
"vulkan12requirements",
|
||||
"vulkan13requirements",
|
||||
"d3d11_baseline"
|
||||
]
|
||||
},
|
||||
"VP_DXVK_d3d11_level_11_0_baseline": {
|
||||
"version": 1,
|
||||
"api-version": "1.3.204",
|
||||
"label": "DXVK D3D11 Level 11.0 Baseline profile",
|
||||
"description": "DXVK for D3D11 Feature Level 11.0 minimum requirements",
|
||||
"capabilities": [
|
||||
"vulkan10requirements",
|
||||
"vulkan11requirements",
|
||||
"vulkan12requirements",
|
||||
"vulkan13requirements",
|
||||
"d3d11_baseline",
|
||||
"d3d11_level11_0"
|
||||
]
|
||||
},
|
||||
"VP_DXVK_d3d11_level_11_1_baseline": {
|
||||
"version": 1,
|
||||
"api-version": "1.3.204",
|
||||
"label": "DXVK D3D11 Level 11.1 Baseline profile",
|
||||
"description": "DXVK for D3D11 Feature Level 11.1 minimum requirements",
|
||||
"capabilities": [
|
||||
"vulkan10requirements",
|
||||
"vulkan11requirements",
|
||||
"vulkan12requirements",
|
||||
"vulkan13requirements",
|
||||
"d3d11_baseline",
|
||||
"d3d11_level11_0",
|
||||
"d3d11_level11_1"
|
||||
]
|
||||
},
|
||||
"VP_DXVK_d3d11_level_11_1_optimal": {
|
||||
"version": 1,
|
||||
"api-version": "1.3.204",
|
||||
"label": "DXVK D3D11 Level 11.1 Optimal profile",
|
||||
"description": "DXVK for D3D11 Feature Level 11.1 including optional capabilities",
|
||||
"capabilities": [
|
||||
"vulkan10requirements",
|
||||
"vulkan11requirements",
|
||||
"vulkan12requirements",
|
||||
"vulkan13requirements",
|
||||
"d3d11_baseline",
|
||||
"d3d11_baseline_optional",
|
||||
"d3d11_level11_0",
|
||||
"d3d11_level11_0_optional",
|
||||
"d3d11_level11_1"
|
||||
]
|
||||
},
|
||||
"VP_DXVK_d3d11_level_12_0_optimal": {
|
||||
"version": 1,
|
||||
"api-version": "1.3.204",
|
||||
"label": "DXVK D3D11 Level 12.0 Optimal profile",
|
||||
"description": "DXVK for D3D11 Feature Level 12.0 including optional capabilities",
|
||||
"capabilities": [
|
||||
"vulkan10requirements",
|
||||
"vulkan11requirements",
|
||||
"vulkan12requirements",
|
||||
"vulkan13requirements",
|
||||
"d3d11_baseline",
|
||||
"d3d11_baseline_optional",
|
||||
"d3d11_level11_0",
|
||||
"d3d11_level11_0_optional",
|
||||
"d3d11_level11_1",
|
||||
"d3d11_level12_0"
|
||||
]
|
||||
}
|
||||
},
|
||||
"contributors": {
|
||||
"Philip Rebohle": {
|
||||
"company": "Valve"
|
||||
},
|
||||
"Joshua Ashton": {
|
||||
"company": "Valve"
|
||||
},
|
||||
"Pierre-Loup A. Griffais": {
|
||||
"company": "Valve"
|
||||
},
|
||||
"Georg Lehmann": {
|
||||
"company": "DXVK"
|
||||
},
|
||||
"Christophe Riccio": {
|
||||
"company": "LunarG"
|
||||
}
|
||||
},
|
||||
"history": [
|
||||
{
|
||||
"revision": 4,
|
||||
"date": "2022-12-18",
|
||||
"author": "Joshua Ashton",
|
||||
"comment": "Add VK_EXT_swapchain_colorspace and VK_EXT_hdr_metadata to d3d11_baseline_optional"
|
||||
},
|
||||
{
|
||||
"revision": 3,
|
||||
"date": "2022-10-13",
|
||||
"author": "Christophe Riccio",
|
||||
"comment": "Factorize history and contributors sections using schema 0.8.1"
|
||||
},
|
||||
{
|
||||
"revision": 2,
|
||||
"date": "2022-08-30",
|
||||
"author": "Philip Rebohle",
|
||||
"comment": "Add VP_DXVK_d3d11_level_12_0_optimal profile"
|
||||
},
|
||||
{
|
||||
"revision": 1,
|
||||
"date": "2022-08-22",
|
||||
"author": "Christophe Riccio",
|
||||
"comment": "Initial revision"
|
||||
}
|
||||
]
|
||||
}
|
240
dxvk.conf
240
dxvk.conf
@ -1,3 +1,15 @@
|
||||
# Expose the HDR10 ColorSpace (DXGI_COLOR_SPACE_RGB_FULL_G2084_NONE_P2020)
|
||||
# to the application by default.
|
||||
# This shows to the game that the global Windows 'HDR Mode' is enabled.
|
||||
# Many (broken) games will need this to be set to consider exposing HDR output
|
||||
# as determine it based on the DXGIOutput's current ColorSpace instead of
|
||||
# using CheckColorSpaceSupport.
|
||||
# This defaults to the value of the DXVK_HDR environment variable.
|
||||
#
|
||||
# Supported values: True, False
|
||||
|
||||
# dxgi.enableHDR = True
|
||||
|
||||
# Create the VkSurface on the first call to IDXGISwapChain::Present,
|
||||
# rather than when creating the swap chain. Some games that start
|
||||
# rendering with a different graphics API may require this option,
|
||||
@ -19,9 +31,10 @@
|
||||
# d3d9.maxFrameLatency = 0
|
||||
|
||||
|
||||
# Enables a frame rate limiter, unless the game is already
|
||||
# limited to the same refresh rate by vertical synchronization.
|
||||
#
|
||||
# Enables frame rate limiter. The main purpose of this is to work around
|
||||
# bugs in games that have physics or other simulation tied to their frame
|
||||
# rate, but do not provide their own limiter.
|
||||
#
|
||||
# Supported values : Any non-negative integer
|
||||
|
||||
# dxgi.maxFrameRate = 0
|
||||
@ -48,14 +61,31 @@
|
||||
# d3d9.customDeviceDesc = ""
|
||||
|
||||
|
||||
# Report Nvidia GPUs as AMD GPUs by default. This is enabled by default
|
||||
# to work around issues with NVAPI, but may cause issues in some games.
|
||||
# Report Nvidia GPUs as AMD GPUs. Unless NVAPI support is explicitly
|
||||
# enabled through proton, this is done by default in order to work
|
||||
# around crashes or low performance with Nvidia-speciic code paths
|
||||
# in games, especially Unreal Engine.
|
||||
#
|
||||
# Supported values: True, False
|
||||
# Supported values: Auto, True, False
|
||||
|
||||
# dxgi.nvapiHack = True
|
||||
# dxgi.hideNvidiaGpu = Auto
|
||||
|
||||
|
||||
# Report AMD GPUs as Nvidia GPUs. This is only done for games that are
|
||||
# known to have issues with AMDAGS or other AMD-specific code paths.
|
||||
#
|
||||
# Supported values: Auto, True, False
|
||||
|
||||
# dxgi.hideAmdGpu = Auto
|
||||
|
||||
|
||||
# Report Intel GPUs as AMD GPUs. This is only done for games that are
|
||||
# known to have issues with Intel-specific libraries such as XESS.
|
||||
#
|
||||
# Supported values: Auto, True, False
|
||||
|
||||
# dxgi.hideIntelGpu = Auto
|
||||
|
||||
|
||||
# Override maximum amount of device memory and shared system memory
|
||||
# reported to the application. This may fix texture streaming issues
|
||||
@ -109,17 +139,7 @@
|
||||
#
|
||||
# Supported values: Auto, True, False
|
||||
|
||||
# dxgi.tearFree = Auto
|
||||
# d3d9.tearFree = Auto
|
||||
|
||||
|
||||
# Performs range check on dynamically indexed constant buffers in shaders.
|
||||
# This may be needed to work around a certain type of game bug, but may
|
||||
# also introduce incorrect behaviour.
|
||||
#
|
||||
# Supported values: True, False
|
||||
|
||||
# d3d11.constantBufferRangeCheck = False
|
||||
# dxvk.tearFree = Auto
|
||||
|
||||
|
||||
# Assume single-use mode for command lists created on deferred contexts.
|
||||
@ -135,9 +155,9 @@
|
||||
# with. Setting this to a higher value may allow some applications to run
|
||||
# that would otherwise fail to create a D3D11 device.
|
||||
#
|
||||
# Supported values: 9_1, 9_2, 9_3, 10_0, 10_1, 11_0, 11_1
|
||||
# Supported values: 9_1, 9_2, 9_3, 10_0, 10_1, 11_0, 11_1, 12_0, 12_1
|
||||
|
||||
# d3d11.maxFeatureLevel = 11_1
|
||||
# d3d11.maxFeatureLevel = 12_1
|
||||
|
||||
|
||||
# Overrides the maximum allowed tessellation factor. This can be used to
|
||||
@ -178,6 +198,26 @@
|
||||
# d3d9.samplerAnisotropy = -1
|
||||
|
||||
|
||||
# Changes the mipmap LOD bias for all samplers. The given number will be
|
||||
# added to the LOD bias provided by the application, rather than replacing
|
||||
# it entirely. Positive values will reduce texture detail, while negative
|
||||
# values may increase sharpness at the cost of shimmer.
|
||||
#
|
||||
# Supported values: Any number between -2.0 and 1.0
|
||||
|
||||
# d3d11.samplerLodBias = 0.0
|
||||
# d3d9.samplerLodBias = 0.0
|
||||
|
||||
|
||||
# Clamps any negative LOD bias to 0. Applies after samplerLodBias has been
|
||||
# applied. May help with games that use a high negative LOD bias by default.
|
||||
#
|
||||
# Supported values: True, False
|
||||
|
||||
# d3d11.clampNegativeLodBias = False
|
||||
# d3d9.clampNegativeLodBias = False
|
||||
|
||||
|
||||
# Declares vertex positions as invariant in order to solve
|
||||
# potential Z-fighting issues at a small performance cost.
|
||||
#
|
||||
@ -187,6 +227,16 @@
|
||||
# d3d9.invariantPosition = True
|
||||
|
||||
|
||||
# Forces per-sample rate shading when MSAA is enabled, rather than per-pixel
|
||||
# shading. May improve visual clarity at a significant performance cost, but
|
||||
# may also introduce visual issues in some games.
|
||||
#
|
||||
# Supported values: True, False
|
||||
|
||||
# d3d11.forceSampleRateShading = False
|
||||
# d3d9.forceSampleRateShading = False
|
||||
|
||||
|
||||
# Forces the sample count of all textures to 1, and performs
|
||||
# the needed fixups in resolve operations and shaders.
|
||||
#
|
||||
@ -234,10 +284,22 @@
|
||||
# d3d11.cachedDynamicResources = ""
|
||||
|
||||
|
||||
# Force-enables the D3D11 context lock via the ID3D10Multithread
|
||||
# interface. This may be useful to debug race conditions.
|
||||
#
|
||||
# Supported values: True, False
|
||||
|
||||
# d3d11.enableContextLock = False
|
||||
|
||||
|
||||
# Sets number of pipeline compiler threads.
|
||||
#
|
||||
# If the graphics pipeline library feature is enabled, the given
|
||||
# number of threads will be used for shader compilation. Some of
|
||||
# these threads will be reserved for high-priority work.
|
||||
#
|
||||
# Supported values:
|
||||
# - 0 to automatically determine the number of threads to use
|
||||
# - 0 to use all available CPU cores
|
||||
# - any positive number to enforce the thread count
|
||||
|
||||
# dxvk.numCompilerThreads = 0
|
||||
@ -258,18 +320,43 @@
|
||||
# dxvk.useRawSsbo = Auto
|
||||
|
||||
|
||||
# Controls Nvidia HVV behaviour.
|
||||
# Changes memory chunk size.
|
||||
#
|
||||
# Disables the host-visible, device-local heap on Nvidia drivers. This
|
||||
# is used to avoid NVIDIA driver bug 3114283 on affected drivers, as
|
||||
# well as in specific games on newer drivers.being enabled on all
|
||||
# affected drivers.
|
||||
# Can be used to override the maximum memory chunk size.
|
||||
#
|
||||
# Supported values:
|
||||
# - Auto: Don't change the default
|
||||
# - True, False: Always enable / disable
|
||||
# - 0 to use the defaults
|
||||
# - any positive integer to limit the chunk size, in MiB
|
||||
|
||||
# dxvk.shrinkNvidiaHvvHeap = Auto
|
||||
# dxvk.maxChunkSize = 0
|
||||
|
||||
|
||||
# Controls graphics pipeline library behaviour
|
||||
#
|
||||
# Can be used to change VK_EXT_graphics_pipeline_library usage for
|
||||
# debugging purpose. Doing so will likely result in increased stutter
|
||||
# or degraded performance.
|
||||
#
|
||||
# Supported values:
|
||||
# - Auto: Enable if supported, and compile optimized pipelines in the background
|
||||
# - True: Enable if supported, but do not compile optimized pipelines
|
||||
# - False: Always disable the feature
|
||||
|
||||
# dxvk.enableGraphicsPipelineLibrary = Auto
|
||||
|
||||
|
||||
# Controls pipeline lifetime tracking
|
||||
#
|
||||
# If enabled, pipeline libraries will be freed aggressively in order
|
||||
# save memory and address space. Has no effect if graphics pipeline
|
||||
# libraries are not supported or disabled.
|
||||
#
|
||||
# Supported values:
|
||||
# - Auto: Enable tracking for 32-bit applications only
|
||||
# - True: Always enable tracking
|
||||
# - False: Always disable tracking
|
||||
|
||||
# dxvk.trackPipelineLifetime = Auto
|
||||
|
||||
|
||||
# Sets enabled HUD elements
|
||||
@ -294,17 +381,6 @@
|
||||
# d3d9.shaderModel = 3
|
||||
|
||||
|
||||
# Evict Managed on Unlock
|
||||
#
|
||||
# Decides whether we should evict managed resources from
|
||||
# system memory when they are unlocked entirely.
|
||||
#
|
||||
# Supported values:
|
||||
# - True, False: Always enable / disable
|
||||
|
||||
# d3d9.evictManagedOnUnlock = False
|
||||
|
||||
|
||||
# DPI Awareness
|
||||
#
|
||||
# Decides whether we should call SetProcessDPIAware on device
|
||||
@ -405,16 +481,6 @@
|
||||
|
||||
# d3d9.longMad = False
|
||||
|
||||
# Alpha Test Wiggle Room
|
||||
#
|
||||
# Workaround for games using alpha test == 1.0, etc due to wonky interpolation or
|
||||
# misc. imprecision on some vendors
|
||||
#
|
||||
# Supported values:
|
||||
# - True/False
|
||||
|
||||
# d3d9.alphaTestWiggleRoom = False
|
||||
|
||||
# Device Local Constant Buffers
|
||||
#
|
||||
# Enables using device local, host accessible memory for constant buffers in D3D9.
|
||||
@ -426,15 +492,6 @@
|
||||
|
||||
# d3d9.deviceLocalConstantBuffers = False
|
||||
|
||||
# No Explicit Front Buffer
|
||||
#
|
||||
# Disables the front buffer
|
||||
#
|
||||
# Supported values:
|
||||
# - True/False
|
||||
|
||||
# d3d9.noExplicitFrontBuffer = False
|
||||
|
||||
# Support DF formats
|
||||
#
|
||||
# Support the vendor extension DF floating point depth formats
|
||||
@ -444,10 +501,19 @@
|
||||
|
||||
# d3d9.supportDFFormats = True
|
||||
|
||||
# Use D32f for D24
|
||||
#
|
||||
# Useful for reproducing AMD issues on other hw.
|
||||
#
|
||||
# Supported values:
|
||||
# - True/False
|
||||
|
||||
# d3d9.useD32forD24 = False
|
||||
|
||||
# Support X4R4G4B4
|
||||
#
|
||||
# Support the X4R4G4B4 format.
|
||||
# The Sims 2 is a horrible game made by complete morons.
|
||||
# The Sims 2 is a very broken game.
|
||||
#
|
||||
# Supported values:
|
||||
# - True/False
|
||||
@ -466,7 +532,7 @@
|
||||
# Disable A8 as a Render Target
|
||||
#
|
||||
# Disable support for A8 format render targets
|
||||
# Once again, The Sims 2 is a horrible game made by complete morons.
|
||||
# Once again, The Sims 2 is a very broken game.
|
||||
#
|
||||
# Supported values:
|
||||
# - True/False
|
||||
@ -506,26 +572,6 @@
|
||||
|
||||
# d3d9.forceAspectRatio = ""
|
||||
|
||||
# Allow Do Not Wait
|
||||
#
|
||||
# Allow the do not wait lock flag to be used
|
||||
# Useful if some apps use this incorrectly.
|
||||
#
|
||||
# Supported values:
|
||||
# - True/False
|
||||
|
||||
# d3d9.allowDoNotWait = True
|
||||
|
||||
# Allow Discard
|
||||
#
|
||||
# Allow the discard lock flag to be used
|
||||
# Useful if some apps use this incorrectly.
|
||||
#
|
||||
# Supported values:
|
||||
# - True/False
|
||||
|
||||
# d3d9.allowDiscard = True
|
||||
|
||||
# Enumerate by Displays
|
||||
#
|
||||
# Whether we should enumerate D3D9 adapters by display (windows behaviour)
|
||||
@ -537,23 +583,43 @@
|
||||
|
||||
# d3d9.enumerateByDisplays = True
|
||||
|
||||
# APITrace Mode
|
||||
# Cached Dynamic Buffers
|
||||
#
|
||||
# Makes all host visible buffers cached and coherent
|
||||
# Improves performance when apitracing, but also can impact
|
||||
# some dumb games.
|
||||
# Allocates dynamic resources in D3DPOOL_DEFAULT in
|
||||
# cached system memory rather than uncached memory or host-visible
|
||||
# VRAM, in order to allow fast readback from the CPU. This is only
|
||||
# useful for buggy applications, and may reduce GPU-bound performance.
|
||||
#
|
||||
# Supported values:
|
||||
# - True/False
|
||||
|
||||
# d3d9.apitraceMode = False
|
||||
# d3d9.cachedDynamicBuffers = False
|
||||
|
||||
# Seamless Cubes
|
||||
#
|
||||
# Don't use non seamless cube maps even if they are supported.
|
||||
# Non seamless cubes are correct d3d9 behavior, but can produce worse looking edges.
|
||||
#
|
||||
# Supported values:
|
||||
# - True/False
|
||||
|
||||
# d3d9.seamlessCubes = False
|
||||
|
||||
# Debug Utils
|
||||
#
|
||||
# Enables debug utils as this is off by default, this enables user annotations like BeginEvent()/EndEvent().
|
||||
# Alternatively could be enabled with DXVK_PERF_EVENTS=1 environment variable.
|
||||
# Alternatively could be enabled with DXVK_DEBUG=markers environment variable.
|
||||
#
|
||||
# Supported values:
|
||||
# - True/False
|
||||
|
||||
# dxvk.enableDebugUtils = False
|
||||
|
||||
# Memory limit for locked D3D9 textures
|
||||
#
|
||||
# How much virtual memory will be used for textures (in MB).
|
||||
# 0 to disable the limit.
|
||||
# THIS DOES NOT IMPACT ACTUAL MEMORY CONSUMPTION OR TEXTURE QUALITY.
|
||||
# DO NOT CHANGE THIS UNLESS YOU HAVE A VERY GOOD REASON.
|
||||
|
||||
# d3d9.textureMemory = 100
|
||||
|
1
include/native/directx
Submodule
1
include/native/directx
Submodule
@ -0,0 +1 @@
|
||||
Subproject commit 9df86f2341616ef1888ae59919feaa6d4fad693d
|
3
include/native/windows/oaidl.h
Normal file
3
include/native/windows/oaidl.h
Normal file
@ -0,0 +1,3 @@
|
||||
#pragma once
|
||||
|
||||
// Don't care.
|
3
include/native/windows/objbase.h
Normal file
3
include/native/windows/objbase.h
Normal file
@ -0,0 +1,3 @@
|
||||
#pragma once
|
||||
|
||||
// Don't care.
|
3
include/native/windows/ocidl.h
Normal file
3
include/native/windows/ocidl.h
Normal file
@ -0,0 +1,3 @@
|
||||
#pragma once
|
||||
|
||||
// Don't care.
|
3
include/native/windows/ole2.h
Normal file
3
include/native/windows/ole2.h
Normal file
@ -0,0 +1,3 @@
|
||||
#pragma once
|
||||
|
||||
// Don't care.
|
8
include/native/windows/poppack.h
Normal file
8
include/native/windows/poppack.h
Normal file
@ -0,0 +1,8 @@
|
||||
/**
|
||||
* This file has no copyright assigned and is placed in the Public Domain.
|
||||
* This file is part of the mingw-w64 runtime package.
|
||||
* No warranty is given; refer to the file DISCLAIMER.PD within this package.
|
||||
*/
|
||||
#if !(defined(lint) || defined(RC_INVOKED))
|
||||
#pragma pack(pop)
|
||||
#endif
|
8
include/native/windows/pshpack4.h
Normal file
8
include/native/windows/pshpack4.h
Normal file
@ -0,0 +1,8 @@
|
||||
/**
|
||||
* This file has no copyright assigned and is placed in the Public Domain.
|
||||
* This file is part of the mingw-w64 runtime package.
|
||||
* No warranty is given; refer to the file DISCLAIMER.PD within this package.
|
||||
*/
|
||||
#if !(defined(lint) || defined(RC_INVOKED))
|
||||
#pragma pack(push,4)
|
||||
#endif
|
3
include/native/windows/rpc.h
Normal file
3
include/native/windows/rpc.h
Normal file
@ -0,0 +1,3 @@
|
||||
#pragma once
|
||||
|
||||
// Don't care.
|
3
include/native/windows/rpcndr.h
Normal file
3
include/native/windows/rpcndr.h
Normal file
@ -0,0 +1,3 @@
|
||||
#pragma once
|
||||
|
||||
// Don't care.
|
52
include/native/windows/unknwn.h
Normal file
52
include/native/windows/unknwn.h
Normal file
@ -0,0 +1,52 @@
|
||||
#pragma once
|
||||
|
||||
#include "windows_base.h"
|
||||
|
||||
typedef interface IUnknown IUnknown;
|
||||
|
||||
DEFINE_GUID(IID_IUnknown, 0x00000000,0x0000,0x0000,0xC0,0x00,0x00,0x00,0x00,0x00,0x00,0x46)
|
||||
|
||||
#ifdef __cplusplus
|
||||
struct IUnknown {
|
||||
|
||||
public:
|
||||
|
||||
virtual HRESULT QueryInterface(REFIID riid, void** ppvObject) = 0;
|
||||
template<class Q>
|
||||
HRESULT STDMETHODCALLTYPE QueryInterface(Q **pp) {
|
||||
return QueryInterface(__uuidof(Q), (void **)pp);
|
||||
}
|
||||
|
||||
virtual ULONG AddRef() = 0;
|
||||
virtual ULONG Release() = 0;
|
||||
|
||||
};
|
||||
#else
|
||||
typedef struct IUnknownVtbl
|
||||
{
|
||||
BEGIN_INTERFACE
|
||||
|
||||
HRESULT (STDMETHODCALLTYPE *QueryInterface)(
|
||||
IUnknown *This,
|
||||
REFIID riid,
|
||||
void **ppvObject
|
||||
);
|
||||
ULONG (STDMETHODCALLTYPE *AddRef)(IUnknown *This);
|
||||
ULONG (STDMETHODCALLTYPE *Release)(IUnknown *This);
|
||||
|
||||
END_INTERFACE
|
||||
} IUnknownVtbl;
|
||||
|
||||
interface IUnknown
|
||||
{
|
||||
CONST_VTBL struct IUnknownVtbl *lpVtbl;
|
||||
};
|
||||
|
||||
#define IUnknown_AddRef(This) ((This)->lpVtbl->AddRef(This))
|
||||
#define IUnknown_Release(This) ((This)->lpVtbl->Release(This))
|
||||
|
||||
#endif // __cplusplus
|
||||
|
||||
DECLARE_UUIDOF_HELPER(IUnknown, 0x00000000,0x0000,0x0000,0xC0,0x00,0x00,0x00,0x00,0x00,0x00,0x46)
|
||||
|
||||
#define IID_PPV_ARGS(ppType) __uuidof(decltype(**(ppType))), [](auto** pp) { (void)static_cast<IUnknown*>(*pp); return reinterpret_cast<void**>(pp); }(ppType)
|
4
include/native/windows/windows.h
Normal file
4
include/native/windows/windows.h
Normal file
@ -0,0 +1,4 @@
|
||||
#pragma once
|
||||
|
||||
#include "windows_base.h"
|
||||
#include "unknwn.h"
|
386
include/native/windows/windows_base.h
Normal file
386
include/native/windows/windows_base.h
Normal file
@ -0,0 +1,386 @@
|
||||
#pragma once
|
||||
|
||||
#ifdef __cplusplus
|
||||
#include <cstdint>
|
||||
#include <cstring>
|
||||
#else
|
||||
#include <stdint.h>
|
||||
#include <string.h>
|
||||
#include <wchar.h>
|
||||
#endif // __cplusplus
|
||||
|
||||
// GCC complains about the COM interfaces
|
||||
// not having virtual destructors
|
||||
|
||||
// and class conversion for C...DESC helper types
|
||||
#if defined(__GNUC__) && defined(__cplusplus)
|
||||
#pragma GCC diagnostic ignored "-Wnon-virtual-dtor"
|
||||
#pragma GCC diagnostic ignored "-Wclass-conversion"
|
||||
#endif // __GNUC__ && __cplusplus
|
||||
|
||||
typedef int32_t INT;
|
||||
typedef uint32_t UINT;
|
||||
|
||||
typedef int32_t LONG;
|
||||
typedef uint32_t ULONG;
|
||||
typedef int32_t *LPLONG;
|
||||
|
||||
typedef int32_t HRESULT;
|
||||
|
||||
typedef wchar_t WCHAR;
|
||||
typedef WCHAR *NWPSTR, *LPWSTR, *PWSTR;
|
||||
typedef unsigned char UCHAR, *PUCHAR;
|
||||
|
||||
typedef char CHAR;
|
||||
typedef const CHAR *LPCSTR, *PCSTR;
|
||||
|
||||
typedef INT BOOL;
|
||||
typedef BOOL WINBOOL;
|
||||
|
||||
typedef uint16_t UINT16;
|
||||
typedef uint32_t UINT32;
|
||||
typedef uint64_t UINT64;
|
||||
typedef void VOID;
|
||||
typedef void* PVOID;
|
||||
typedef void* LPVOID;
|
||||
typedef const void* LPCVOID;
|
||||
|
||||
typedef size_t SIZE_T;
|
||||
|
||||
typedef int8_t INT8;
|
||||
|
||||
typedef uint8_t UINT8;
|
||||
typedef uint8_t BYTE;
|
||||
|
||||
typedef int16_t SHORT;
|
||||
typedef uint16_t USHORT;
|
||||
|
||||
typedef int64_t LONGLONG;
|
||||
typedef uint64_t ULONGLONG;
|
||||
|
||||
typedef intptr_t LONG_PTR;
|
||||
|
||||
typedef float FLOAT;
|
||||
|
||||
#ifndef GUID_DEFINED
|
||||
#define GUID_DEFINED
|
||||
typedef struct GUID {
|
||||
uint32_t Data1;
|
||||
uint16_t Data2;
|
||||
uint16_t Data3;
|
||||
uint8_t Data4[8];
|
||||
} GUID;
|
||||
#endif // GUID_DEFINED
|
||||
|
||||
typedef GUID UUID;
|
||||
typedef GUID IID;
|
||||
#ifdef __cplusplus
|
||||
#define REFIID const IID&
|
||||
#define REFGUID const GUID&
|
||||
#define REFCLSID const GUID&
|
||||
#else
|
||||
#define REFIID const IID*
|
||||
#define REFGUID const GUID*
|
||||
#define REFCLSID const GUID* const
|
||||
#endif // __cplusplus
|
||||
|
||||
#ifdef __cplusplus
|
||||
|
||||
template <typename T>
|
||||
constexpr GUID __uuidof_helper();
|
||||
|
||||
#define __uuidof(T) __uuidof_helper<T>()
|
||||
#define __uuidof_var(T) __uuidof_helper<decltype(T)>()
|
||||
|
||||
inline bool operator==(const GUID& a, const GUID& b) { return std::memcmp(&a, &b, sizeof(GUID)) == 0; }
|
||||
inline bool operator!=(const GUID& a, const GUID& b) { return std::memcmp(&a, &b, sizeof(GUID)) != 0; }
|
||||
|
||||
#endif // __cplusplus
|
||||
|
||||
typedef uint32_t DWORD;
|
||||
typedef uint16_t WORD;
|
||||
typedef DWORD *LPDWORD;
|
||||
|
||||
typedef void* HANDLE;
|
||||
typedef HANDLE HMONITOR;
|
||||
typedef HANDLE HDC;
|
||||
typedef HANDLE HMODULE;
|
||||
typedef HANDLE HINSTANCE;
|
||||
typedef HANDLE HWND;
|
||||
typedef HANDLE HKEY;
|
||||
typedef HANDLE *LPHANDLE;
|
||||
typedef DWORD COLORREF;
|
||||
|
||||
#if INTPTR_MAX == INT64_MAX
|
||||
typedef int64_t INT_PTR;
|
||||
typedef uint64_t UINT_PTR;
|
||||
#else
|
||||
typedef int32_t INT_PTR;
|
||||
typedef uint32_t UINT_PTR;
|
||||
#endif
|
||||
typedef INT_PTR* PINT_PTR;
|
||||
typedef UINT_PTR* PUINT_PTR;
|
||||
|
||||
#ifdef STRICT
|
||||
#define DECLARE_HANDLE(a) typedef struct a##__ { int unused; } *a
|
||||
#else /*STRICT*/
|
||||
#define DECLARE_HANDLE(a) typedef HANDLE a
|
||||
#endif /*STRICT*/
|
||||
|
||||
typedef char* LPSTR;
|
||||
typedef wchar_t* LPWSTR;
|
||||
typedef const char* LPCSTR;
|
||||
typedef const wchar_t* LPCWSTR;
|
||||
|
||||
typedef struct LUID {
|
||||
DWORD LowPart;
|
||||
LONG HighPart;
|
||||
} LUID;
|
||||
|
||||
typedef struct POINT {
|
||||
LONG x;
|
||||
LONG y;
|
||||
} POINT;
|
||||
|
||||
typedef POINT* LPPOINT;
|
||||
|
||||
typedef struct RECT {
|
||||
LONG left;
|
||||
LONG top;
|
||||
LONG right;
|
||||
LONG bottom;
|
||||
} RECT,*PRECT,*NPRECT,*LPRECT;
|
||||
|
||||
typedef struct SIZE {
|
||||
LONG cx;
|
||||
LONG cy;
|
||||
} SIZE,*PSIZE,*LPSIZE;
|
||||
|
||||
typedef union {
|
||||
struct {
|
||||
DWORD LowPart;
|
||||
LONG HighPart;
|
||||
};
|
||||
|
||||
struct {
|
||||
DWORD LowPart;
|
||||
LONG HighPart;
|
||||
} u;
|
||||
|
||||
LONGLONG QuadPart;
|
||||
} LARGE_INTEGER;
|
||||
|
||||
typedef struct MEMORYSTATUS {
|
||||
DWORD dwLength;
|
||||
SIZE_T dwTotalPhys;
|
||||
} MEMORYSTATUS;
|
||||
|
||||
typedef struct SECURITY_ATTRIBUTES {
|
||||
DWORD nLength;
|
||||
void* lpSecurityDescriptor;
|
||||
BOOL bInheritHandle;
|
||||
} SECURITY_ATTRIBUTES;
|
||||
|
||||
typedef struct PALETTEENTRY {
|
||||
BYTE peRed;
|
||||
BYTE peGreen;
|
||||
BYTE peBlue;
|
||||
BYTE peFlags;
|
||||
} PALETTEENTRY, *PPALETTEENTRY, *LPPALETTEENTRY;
|
||||
|
||||
typedef struct RGNDATAHEADER {
|
||||
DWORD dwSize;
|
||||
DWORD iType;
|
||||
DWORD nCount;
|
||||
DWORD nRgnSize;
|
||||
RECT rcBound;
|
||||
} RGNDATAHEADER;
|
||||
|
||||
typedef struct RGNDATA {
|
||||
RGNDATAHEADER rdh;
|
||||
char Buffer[1];
|
||||
} RGNDATA,*PRGNDATA,*NPRGNDATA,*LPRGNDATA;
|
||||
|
||||
// Ignore these.
|
||||
#define STDMETHODCALLTYPE
|
||||
#define __stdcall
|
||||
|
||||
#define CONST const
|
||||
#define CONST_VTBL const
|
||||
|
||||
#define TRUE 1
|
||||
#define FALSE 0
|
||||
|
||||
#define WAIT_TIMEOUT 0x00000102
|
||||
#define WAIT_FAILED 0xffffffff
|
||||
#define WAIT_OBJECT_0 0
|
||||
#define WAIT_ABANDONED 0x00000080
|
||||
|
||||
#define interface struct
|
||||
#define MIDL_INTERFACE(x) struct
|
||||
|
||||
#ifdef __cplusplus
|
||||
|
||||
#define DEFINE_GUID(iid, a, b, c, d, e, f, g, h, i, j, k) \
|
||||
constexpr GUID iid = {a,b,c,{d,e,f,g,h,i,j,k}};
|
||||
|
||||
#define DECLARE_UUIDOF_HELPER(type, a, b, c, d, e, f, g, h, i, j, k) \
|
||||
extern "C++" { template <> constexpr GUID __uuidof_helper<type>() { return GUID{a,b,c,{d,e,f,g,h,i,j,k}}; } } \
|
||||
extern "C++" { template <> constexpr GUID __uuidof_helper<type*>() { return __uuidof_helper<type>(); } } \
|
||||
extern "C++" { template <> constexpr GUID __uuidof_helper<const type*>() { return __uuidof_helper<type>(); } } \
|
||||
extern "C++" { template <> constexpr GUID __uuidof_helper<type&>() { return __uuidof_helper<type>(); } } \
|
||||
extern "C++" { template <> constexpr GUID __uuidof_helper<const type&>() { return __uuidof_helper<type>(); } }
|
||||
|
||||
#else
|
||||
#define DEFINE_GUID(iid, a, b, c, d, e, f, g, h, i, j, k) \
|
||||
static const GUID iid = {a,b,c,{d,e,f,g,h,i,j,k}};
|
||||
#define DECLARE_UUIDOF_HELPER(type, a, b, c, d, e, f, g, h, i, j, k)
|
||||
#endif // __cplusplus
|
||||
|
||||
#define __CRT_UUID_DECL(type, a, b, c, d, e, f, g, h, i, j, k) DECLARE_UUIDOF_HELPER(type, a, b, c, d, e, f, g, h, i, j, k)
|
||||
|
||||
#define S_OK 0
|
||||
#define S_FALSE 1
|
||||
|
||||
#define E_INVALIDARG ((HRESULT)0x80070057)
|
||||
#define E_FAIL ((HRESULT)0x80004005)
|
||||
#define E_NOINTERFACE ((HRESULT)0x80004002)
|
||||
#define E_NOTIMPL ((HRESULT)0x80004001)
|
||||
#define E_OUTOFMEMORY ((HRESULT)0x8007000E)
|
||||
#define E_POINTER ((HRESULT)0x80004003)
|
||||
|
||||
#define DXGI_STATUS_OCCLUDED ((HRESULT)0x087a0001)
|
||||
#define DXGI_STATUS_CLIPPED ((HRESULT)0x087a0002)
|
||||
#define DXGI_STATUS_NO_REDIRECTION ((HRESULT)0x087a0004)
|
||||
#define DXGI_STATUS_NO_DESKTOP_ACCESS ((HRESULT)0x087a0005)
|
||||
#define DXGI_STATUS_GRAPHICS_VIDPN_SOURCE_IN_USE ((HRESULT)0x087a0006)
|
||||
#define DXGI_STATUS_MODE_CHANGED ((HRESULT)0x087a0007)
|
||||
#define DXGI_STATUS_MODE_CHANGE_IN_PROGRESS ((HRESULT)0x087a0008)
|
||||
#define DXGI_STATUS_UNOCCLUDED ((HRESULT)0x087a0009)
|
||||
#define DXGI_STATUS_DDA_WAS_STILL_DRAWING ((HRESULT)0x087a000a)
|
||||
#define DXGI_STATUS_PRESENT_REQUIRED ((HRESULT)0x087a002f)
|
||||
|
||||
#define DXGI_ERROR_INVALID_CALL ((HRESULT)0x887A0001)
|
||||
#define DXGI_ERROR_NOT_FOUND ((HRESULT)0x887A0002)
|
||||
#define DXGI_ERROR_MORE_DATA ((HRESULT)0x887A0003)
|
||||
#define DXGI_ERROR_UNSUPPORTED ((HRESULT)0x887A0004)
|
||||
#define DXGI_ERROR_DEVICE_REMOVED ((HRESULT)0x887A0005)
|
||||
#define DXGI_ERROR_DEVICE_HUNG ((HRESULT)0x887A0006)
|
||||
#define DXGI_ERROR_DEVICE_RESET ((HRESULT)0x887A0007)
|
||||
#define DXGI_ERROR_WAS_STILL_DRAWING ((HRESULT)0x887A000A)
|
||||
#define DXGI_ERROR_FRAME_STATISTICS_DISJOINT ((HRESULT)0x887A000B)
|
||||
#define DXGI_ERROR_GRAPHICS_VIDPN_SOURCE_IN_USE ((HRESULT)0x887A000C)
|
||||
#define DXGI_ERROR_DRIVER_INTERNAL_ERROR ((HRESULT)0x887A0020)
|
||||
#define DXGI_ERROR_NONEXCLUSIVE ((HRESULT)0x887A0021)
|
||||
#define DXGI_ERROR_NOT_CURRENTLY_AVAILABLE ((HRESULT)0x887A0022)
|
||||
#define DXGI_ERROR_REMOTE_CLIENT_DISCONNECTED ((HRESULT)0x887A0023)
|
||||
#define DXGI_ERROR_REMOTE_OUTOFMEMORY ((HRESULT)0x887A0024)
|
||||
#define DXGI_ERROR_ACCESS_LOST ((HRESULT)0x887A0026)
|
||||
#define DXGI_ERROR_WAIT_TIMEOUT ((HRESULT)0x887A0027)
|
||||
#define DXGI_ERROR_SESSION_DISCONNECTED ((HRESULT)0x887A0028)
|
||||
#define DXGI_ERROR_RESTRICT_TO_OUTPUT_STALE ((HRESULT)0x887A0029)
|
||||
#define DXGI_ERROR_CANNOT_PROTECT_CONTENT ((HRESULT)0x887A002A)
|
||||
#define DXGI_ERROR_ACCESS_DENIED ((HRESULT)0x887A002B)
|
||||
#define DXGI_ERROR_NAME_ALREADY_EXISTS ((HRESULT)0x887A002C)
|
||||
#define DXGI_ERROR_SDK_COMPONENT_MISSING ((HRESULT)0x887A002D)
|
||||
|
||||
#define WINAPI
|
||||
#define WINUSERAPI
|
||||
|
||||
#define RGB(r,g,b) ((COLORREF)(((BYTE)(r)|((WORD)((BYTE)(g))<<8))|(((DWORD)(BYTE)(b))<<16)))
|
||||
|
||||
#define MAKE_HRESULT(sev,fac,code) \
|
||||
((HRESULT) (((unsigned long)(sev)<<31) | ((unsigned long)(fac)<<16) | ((unsigned long)(code))) )
|
||||
|
||||
#ifdef __cplusplus
|
||||
#define STDMETHOD(name) virtual HRESULT name
|
||||
#define STDMETHOD_(type, name) virtual type name
|
||||
#else
|
||||
#define STDMETHOD(name) HRESULT (STDMETHODCALLTYPE *name)
|
||||
#define STDMETHOD_(type, name) type (STDMETHODCALLTYPE *name)
|
||||
#endif // __cplusplus
|
||||
|
||||
#define THIS_
|
||||
#define THIS
|
||||
|
||||
#define __C89_NAMELESSSTRUCTNAME
|
||||
#define __C89_NAMELESSUNIONNAME
|
||||
#define __C89_NAMELESSUNIONNAME1
|
||||
#define __C89_NAMELESSUNIONNAME2
|
||||
#define __C89_NAMELESSUNIONNAME3
|
||||
#define __C89_NAMELESSUNIONNAME4
|
||||
#define __C89_NAMELESSUNIONNAME5
|
||||
#define __C89_NAMELESSUNIONNAME6
|
||||
#define __C89_NAMELESSUNIONNAME7
|
||||
#define __C89_NAMELESSUNIONNAME8
|
||||
#define __C89_NAMELESS
|
||||
#define DUMMYUNIONNAME
|
||||
#define DUMMYSTRUCTNAME
|
||||
#define DUMMYUNIONNAME1
|
||||
#define DUMMYUNIONNAME2
|
||||
#define DUMMYUNIONNAME3
|
||||
#define DUMMYUNIONNAME4
|
||||
#define DUMMYUNIONNAME5
|
||||
#define DUMMYUNIONNAME6
|
||||
#define DUMMYUNIONNAME7
|
||||
#define DUMMYUNIONNAME8
|
||||
#define DUMMYUNIONNAME9
|
||||
|
||||
#ifdef __cplusplus
|
||||
#define DECLARE_INTERFACE(x) struct x
|
||||
#define DECLARE_INTERFACE_(x, y) struct x : public y
|
||||
#else
|
||||
#define DECLARE_INTERFACE(x) \
|
||||
typedef interface x { \
|
||||
const struct x##Vtbl *lpVtbl; \
|
||||
} x; \
|
||||
typedef const struct x##Vtbl x##Vtbl; \
|
||||
const struct x##Vtbl
|
||||
#define DECLARE_INTERFACE_(x, y) DECLARE_INTERFACE(x)
|
||||
#endif // __cplusplus
|
||||
|
||||
#define BEGIN_INTERFACE
|
||||
#define END_INTERFACE
|
||||
|
||||
#ifdef __cplusplus
|
||||
#define PURE = 0
|
||||
#else
|
||||
#define PURE
|
||||
#endif // __cplusplus
|
||||
|
||||
#define DECLSPEC_SELECTANY
|
||||
|
||||
#define __MSABI_LONG(x) x
|
||||
|
||||
#define ENUM_CURRENT_SETTINGS ((DWORD)-1)
|
||||
#define ENUM_REGISTRY_SETTINGS ((DWORD)-2)
|
||||
|
||||
#define INVALID_HANDLE_VALUE ((HANDLE)-1)
|
||||
|
||||
#define DUPLICATE_CLOSE_SOURCE ((DWORD)0x1)
|
||||
#define DUPLICATE_SAME_ACCESS ((DWORD)0x2)
|
||||
|
||||
#define FAILED(hr) ((HRESULT)(hr) < 0)
|
||||
#define SUCCEEDED(hr) ((HRESULT)(hr) >= 0)
|
||||
|
||||
#define RtlZeroMemory(Destination,Length) memset((Destination),0,(Length))
|
||||
#define ZeroMemory RtlZeroMemory
|
||||
|
||||
#ifndef DEFINE_ENUM_FLAG_OPERATORS
|
||||
|
||||
#ifdef __cplusplus
|
||||
# define DEFINE_ENUM_FLAG_OPERATORS(type) \
|
||||
extern "C++" \
|
||||
{ \
|
||||
inline type operator &(type x, type y) { return (type)((int)x & (int)y); } \
|
||||
inline type operator &=(type &x, type y) { return (type &)((int &)x &= (int)y); } \
|
||||
inline type operator ~(type x) { return (type)~(int)x; } \
|
||||
inline type operator |(type x, type y) { return (type)((int)x | (int)y); } \
|
||||
inline type operator |=(type &x, type y) { return (type &)((int &)x |= (int)y); } \
|
||||
inline type operator ^(type x, type y) { return (type)((int)x ^ (int)y); } \
|
||||
inline type operator ^=(type &x, type y) { return (type &)((int &)x ^= (int)y); } \
|
||||
}
|
||||
#else
|
||||
# define DEFINE_ENUM_FLAG_OPERATORS(type)
|
||||
#endif
|
||||
#endif /* DEFINE_ENUM_FLAG_OPERATORS */
|
25
include/native/wsi/native_glfw.h
Normal file
25
include/native/wsi/native_glfw.h
Normal file
@ -0,0 +1,25 @@
|
||||
#include <windows.h>
|
||||
|
||||
#include <GLFW/glfw3.h>
|
||||
|
||||
namespace dxvk::wsi {
|
||||
|
||||
inline GLFWwindow* fromHwnd(HWND hWindow) {
|
||||
return reinterpret_cast<GLFWwindow*>(hWindow);
|
||||
}
|
||||
|
||||
inline HWND toHwnd(GLFWwindow* pWindow) {
|
||||
return reinterpret_cast<HWND>(pWindow);
|
||||
}
|
||||
|
||||
// Offset so null HMONITORs go to -1
|
||||
inline int32_t fromHmonitor(HMONITOR hMonitor) {
|
||||
return static_cast<int32_t>(reinterpret_cast<intptr_t>(hMonitor)) - 1;
|
||||
}
|
||||
|
||||
// Offset so -1 display id goes to 0 == NULL
|
||||
inline HMONITOR toHmonitor(int32_t displayId) {
|
||||
return reinterpret_cast<HMONITOR>(static_cast<intptr_t>(displayId + 1));
|
||||
}
|
||||
|
||||
}
|
25
include/native/wsi/native_sdl2.h
Normal file
25
include/native/wsi/native_sdl2.h
Normal file
@ -0,0 +1,25 @@
|
||||
#include <windows.h>
|
||||
|
||||
#include <SDL2/SDL.h>
|
||||
|
||||
namespace dxvk::wsi {
|
||||
|
||||
inline SDL_Window* fromHwnd(HWND hWindow) {
|
||||
return reinterpret_cast<SDL_Window*>(hWindow);
|
||||
}
|
||||
|
||||
inline HWND toHwnd(SDL_Window* pWindow) {
|
||||
return reinterpret_cast<HWND>(pWindow);
|
||||
}
|
||||
|
||||
// Offset so null HMONITORs go to -1
|
||||
inline int32_t fromHmonitor(HMONITOR hMonitor) {
|
||||
return static_cast<int32_t>(reinterpret_cast<intptr_t>(hMonitor)) - 1;
|
||||
}
|
||||
|
||||
// Offset so -1 display id goes to 0 == NULL
|
||||
inline HMONITOR toHmonitor(int32_t displayId) {
|
||||
return reinterpret_cast<HMONITOR>(static_cast<intptr_t>(displayId + 1));
|
||||
}
|
||||
|
||||
}
|
11
include/native/wsi/native_wsi.h
Normal file
11
include/native/wsi/native_wsi.h
Normal file
@ -0,0 +1,11 @@
|
||||
#pragma once
|
||||
|
||||
#ifdef DXVK_WSI_WIN32
|
||||
#error You shouldnt be using this code path.
|
||||
#elif DXVK_WSI_SDL2
|
||||
#include "wsi/native_sdl2.h"
|
||||
#elif DXVK_WSI_GLFW
|
||||
#include "wsi/native_glfw.h"
|
||||
#else
|
||||
#error Unknown wsi!
|
||||
#endif
|
1
include/spirv
Submodule
1
include/spirv
Submodule
@ -0,0 +1 @@
|
||||
Subproject commit 0bcc624926a25a2a273d07877fd25a6ff5ba1cfb
|
@ -1,131 +0,0 @@
|
||||
/*
|
||||
** Copyright (c) 2014-2016 The Khronos Group Inc.
|
||||
**
|
||||
** Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
** of this software and/or associated documentation files (the "Materials"),
|
||||
** to deal in the Materials without restriction, including without limitation
|
||||
** the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
** and/or sell copies of the Materials, and to permit persons to whom the
|
||||
** Materials are furnished to do so, subject to the following conditions:
|
||||
**
|
||||
** The above copyright notice and this permission notice shall be included in
|
||||
** all copies or substantial portions of the Materials.
|
||||
**
|
||||
** MODIFICATIONS TO THIS FILE MAY MEAN IT NO LONGER ACCURATELY REFLECTS KHRONOS
|
||||
** STANDARDS. THE UNMODIFIED, NORMATIVE VERSIONS OF KHRONOS SPECIFICATIONS AND
|
||||
** HEADER INFORMATION ARE LOCATED AT https://www.khronos.org/registry/
|
||||
**
|
||||
** THE MATERIALS ARE PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
|
||||
** OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
** FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
** THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
** LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
** FROM,OUT OF OR IN CONNECTION WITH THE MATERIALS OR THE USE OR OTHER DEALINGS
|
||||
** IN THE MATERIALS.
|
||||
*/
|
||||
|
||||
#ifndef GLSLstd450_H
|
||||
#define GLSLstd450_H
|
||||
|
||||
static const int GLSLstd450Version = 100;
|
||||
static const int GLSLstd450Revision = 3;
|
||||
|
||||
enum GLSLstd450 {
|
||||
GLSLstd450Bad = 0, // Don't use
|
||||
|
||||
GLSLstd450Round = 1,
|
||||
GLSLstd450RoundEven = 2,
|
||||
GLSLstd450Trunc = 3,
|
||||
GLSLstd450FAbs = 4,
|
||||
GLSLstd450SAbs = 5,
|
||||
GLSLstd450FSign = 6,
|
||||
GLSLstd450SSign = 7,
|
||||
GLSLstd450Floor = 8,
|
||||
GLSLstd450Ceil = 9,
|
||||
GLSLstd450Fract = 10,
|
||||
|
||||
GLSLstd450Radians = 11,
|
||||
GLSLstd450Degrees = 12,
|
||||
GLSLstd450Sin = 13,
|
||||
GLSLstd450Cos = 14,
|
||||
GLSLstd450Tan = 15,
|
||||
GLSLstd450Asin = 16,
|
||||
GLSLstd450Acos = 17,
|
||||
GLSLstd450Atan = 18,
|
||||
GLSLstd450Sinh = 19,
|
||||
GLSLstd450Cosh = 20,
|
||||
GLSLstd450Tanh = 21,
|
||||
GLSLstd450Asinh = 22,
|
||||
GLSLstd450Acosh = 23,
|
||||
GLSLstd450Atanh = 24,
|
||||
GLSLstd450Atan2 = 25,
|
||||
|
||||
GLSLstd450Pow = 26,
|
||||
GLSLstd450Exp = 27,
|
||||
GLSLstd450Log = 28,
|
||||
GLSLstd450Exp2 = 29,
|
||||
GLSLstd450Log2 = 30,
|
||||
GLSLstd450Sqrt = 31,
|
||||
GLSLstd450InverseSqrt = 32,
|
||||
|
||||
GLSLstd450Determinant = 33,
|
||||
GLSLstd450MatrixInverse = 34,
|
||||
|
||||
GLSLstd450Modf = 35, // second operand needs an OpVariable to write to
|
||||
GLSLstd450ModfStruct = 36, // no OpVariable operand
|
||||
GLSLstd450FMin = 37,
|
||||
GLSLstd450UMin = 38,
|
||||
GLSLstd450SMin = 39,
|
||||
GLSLstd450FMax = 40,
|
||||
GLSLstd450UMax = 41,
|
||||
GLSLstd450SMax = 42,
|
||||
GLSLstd450FClamp = 43,
|
||||
GLSLstd450UClamp = 44,
|
||||
GLSLstd450SClamp = 45,
|
||||
GLSLstd450FMix = 46,
|
||||
GLSLstd450IMix = 47, // Reserved
|
||||
GLSLstd450Step = 48,
|
||||
GLSLstd450SmoothStep = 49,
|
||||
|
||||
GLSLstd450Fma = 50,
|
||||
GLSLstd450Frexp = 51, // second operand needs an OpVariable to write to
|
||||
GLSLstd450FrexpStruct = 52, // no OpVariable operand
|
||||
GLSLstd450Ldexp = 53,
|
||||
|
||||
GLSLstd450PackSnorm4x8 = 54,
|
||||
GLSLstd450PackUnorm4x8 = 55,
|
||||
GLSLstd450PackSnorm2x16 = 56,
|
||||
GLSLstd450PackUnorm2x16 = 57,
|
||||
GLSLstd450PackHalf2x16 = 58,
|
||||
GLSLstd450PackDouble2x32 = 59,
|
||||
GLSLstd450UnpackSnorm2x16 = 60,
|
||||
GLSLstd450UnpackUnorm2x16 = 61,
|
||||
GLSLstd450UnpackHalf2x16 = 62,
|
||||
GLSLstd450UnpackSnorm4x8 = 63,
|
||||
GLSLstd450UnpackUnorm4x8 = 64,
|
||||
GLSLstd450UnpackDouble2x32 = 65,
|
||||
|
||||
GLSLstd450Length = 66,
|
||||
GLSLstd450Distance = 67,
|
||||
GLSLstd450Cross = 68,
|
||||
GLSLstd450Normalize = 69,
|
||||
GLSLstd450FaceForward = 70,
|
||||
GLSLstd450Reflect = 71,
|
||||
GLSLstd450Refract = 72,
|
||||
|
||||
GLSLstd450FindILsb = 73,
|
||||
GLSLstd450FindSMsb = 74,
|
||||
GLSLstd450FindUMsb = 75,
|
||||
|
||||
GLSLstd450InterpolateAtCentroid = 76,
|
||||
GLSLstd450InterpolateAtSample = 77,
|
||||
GLSLstd450InterpolateAtOffset = 78,
|
||||
|
||||
GLSLstd450NMin = 79,
|
||||
GLSLstd450NMax = 80,
|
||||
GLSLstd450NClamp = 81,
|
||||
|
||||
GLSLstd450Count
|
||||
};
|
||||
|
||||
#endif // #ifndef GLSLstd450_H
|
@ -1,135 +0,0 @@
|
||||
/*
|
||||
** Copyright (c) 2014-2016 The Khronos Group Inc.
|
||||
**
|
||||
** Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
** of this software and/or associated documentation files (the "Materials"),
|
||||
** to deal in the Materials without restriction, including without limitation
|
||||
** the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
** and/or sell copies of the Materials, and to permit persons to whom the
|
||||
** Materials are furnished to do so, subject to the following conditions:
|
||||
**
|
||||
** The above copyright notice and this permission notice shall be included in
|
||||
** all copies or substantial portions of the Materials.
|
||||
**
|
||||
** MODIFICATIONS TO THIS FILE MAY MEAN IT NO LONGER ACCURATELY REFLECTS KHRONOS
|
||||
** STANDARDS. THE UNMODIFIED, NORMATIVE VERSIONS OF KHRONOS SPECIFICATIONS AND
|
||||
** HEADER INFORMATION ARE LOCATED AT https://www.khronos.org/registry/
|
||||
**
|
||||
** THE MATERIALS ARE PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
|
||||
** OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
** FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
** THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
** LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
** FROM,OUT OF OR IN CONNECTION WITH THE MATERIALS OR THE USE OR OTHER DEALINGS
|
||||
** IN THE MATERIALS.
|
||||
*/
|
||||
|
||||
#ifndef GLSLstd450_HPP
|
||||
#define GLSLstd450_HPP
|
||||
|
||||
namespace spv {
|
||||
|
||||
static const int GLSLstd450Version = 100;
|
||||
static const int GLSLstd450Revision = 3;
|
||||
|
||||
enum GLSLstd450 {
|
||||
GLSLstd450Bad = 0, // Don't use
|
||||
|
||||
GLSLstd450Round = 1,
|
||||
GLSLstd450RoundEven = 2,
|
||||
GLSLstd450Trunc = 3,
|
||||
GLSLstd450FAbs = 4,
|
||||
GLSLstd450SAbs = 5,
|
||||
GLSLstd450FSign = 6,
|
||||
GLSLstd450SSign = 7,
|
||||
GLSLstd450Floor = 8,
|
||||
GLSLstd450Ceil = 9,
|
||||
GLSLstd450Fract = 10,
|
||||
|
||||
GLSLstd450Radians = 11,
|
||||
GLSLstd450Degrees = 12,
|
||||
GLSLstd450Sin = 13,
|
||||
GLSLstd450Cos = 14,
|
||||
GLSLstd450Tan = 15,
|
||||
GLSLstd450Asin = 16,
|
||||
GLSLstd450Acos = 17,
|
||||
GLSLstd450Atan = 18,
|
||||
GLSLstd450Sinh = 19,
|
||||
GLSLstd450Cosh = 20,
|
||||
GLSLstd450Tanh = 21,
|
||||
GLSLstd450Asinh = 22,
|
||||
GLSLstd450Acosh = 23,
|
||||
GLSLstd450Atanh = 24,
|
||||
GLSLstd450Atan2 = 25,
|
||||
|
||||
GLSLstd450Pow = 26,
|
||||
GLSLstd450Exp = 27,
|
||||
GLSLstd450Log = 28,
|
||||
GLSLstd450Exp2 = 29,
|
||||
GLSLstd450Log2 = 30,
|
||||
GLSLstd450Sqrt = 31,
|
||||
GLSLstd450InverseSqrt = 32,
|
||||
|
||||
GLSLstd450Determinant = 33,
|
||||
GLSLstd450MatrixInverse = 34,
|
||||
|
||||
GLSLstd450Modf = 35, // second operand needs an OpVariable to write to
|
||||
GLSLstd450ModfStruct = 36, // no OpVariable operand
|
||||
GLSLstd450FMin = 37,
|
||||
GLSLstd450UMin = 38,
|
||||
GLSLstd450SMin = 39,
|
||||
GLSLstd450FMax = 40,
|
||||
GLSLstd450UMax = 41,
|
||||
GLSLstd450SMax = 42,
|
||||
GLSLstd450FClamp = 43,
|
||||
GLSLstd450UClamp = 44,
|
||||
GLSLstd450SClamp = 45,
|
||||
GLSLstd450FMix = 46,
|
||||
GLSLstd450IMix = 47, // Reserved
|
||||
GLSLstd450Step = 48,
|
||||
GLSLstd450SmoothStep = 49,
|
||||
|
||||
GLSLstd450Fma = 50,
|
||||
GLSLstd450Frexp = 51, // second operand needs an OpVariable to write to
|
||||
GLSLstd450FrexpStruct = 52, // no OpVariable operand
|
||||
GLSLstd450Ldexp = 53,
|
||||
|
||||
GLSLstd450PackSnorm4x8 = 54,
|
||||
GLSLstd450PackUnorm4x8 = 55,
|
||||
GLSLstd450PackSnorm2x16 = 56,
|
||||
GLSLstd450PackUnorm2x16 = 57,
|
||||
GLSLstd450PackHalf2x16 = 58,
|
||||
GLSLstd450PackDouble2x32 = 59,
|
||||
GLSLstd450UnpackSnorm2x16 = 60,
|
||||
GLSLstd450UnpackUnorm2x16 = 61,
|
||||
GLSLstd450UnpackHalf2x16 = 62,
|
||||
GLSLstd450UnpackSnorm4x8 = 63,
|
||||
GLSLstd450UnpackUnorm4x8 = 64,
|
||||
GLSLstd450UnpackDouble2x32 = 65,
|
||||
|
||||
GLSLstd450Length = 66,
|
||||
GLSLstd450Distance = 67,
|
||||
GLSLstd450Cross = 68,
|
||||
GLSLstd450Normalize = 69,
|
||||
GLSLstd450FaceForward = 70,
|
||||
GLSLstd450Reflect = 71,
|
||||
GLSLstd450Refract = 72,
|
||||
|
||||
GLSLstd450FindILsb = 73,
|
||||
GLSLstd450FindSMsb = 74,
|
||||
GLSLstd450FindUMsb = 75,
|
||||
|
||||
GLSLstd450InterpolateAtCentroid = 76,
|
||||
GLSLstd450InterpolateAtSample = 77,
|
||||
GLSLstd450InterpolateAtOffset = 78,
|
||||
|
||||
GLSLstd450NMin = 79,
|
||||
GLSLstd450NMax = 80,
|
||||
GLSLstd450NClamp = 81,
|
||||
|
||||
GLSLstd450Count
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
#endif // #ifndef GLSLstd450_HPP
|
@ -1,1934 +0,0 @@
|
||||
// Copyright (c) 2014-2019 The Khronos Group Inc.
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and/or associated documentation files (the "Materials"),
|
||||
// to deal in the Materials without restriction, including without limitation
|
||||
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
// and/or sell copies of the Materials, and to permit persons to whom the
|
||||
// Materials are furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Materials.
|
||||
//
|
||||
// MODIFICATIONS TO THIS FILE MAY MEAN IT NO LONGER ACCURATELY REFLECTS KHRONOS
|
||||
// STANDARDS. THE UNMODIFIED, NORMATIVE VERSIONS OF KHRONOS SPECIFICATIONS AND
|
||||
// HEADER INFORMATION ARE LOCATED AT https://www.khronos.org/registry/
|
||||
//
|
||||
// THE MATERIALS ARE PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
|
||||
// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM,OUT OF OR IN CONNECTION WITH THE MATERIALS OR THE USE OR OTHER DEALINGS
|
||||
// IN THE MATERIALS.
|
||||
|
||||
// This header is automatically generated by the same tool that creates
|
||||
// the Binary Section of the SPIR-V specification.
|
||||
|
||||
// Enumeration tokens for SPIR-V, in various styles:
|
||||
// C, C++, C++11, JSON, Lua, Python, C#, D
|
||||
//
|
||||
// - C will have tokens with a "Spv" prefix, e.g.: SpvSourceLanguageGLSL
|
||||
// - C++ will have tokens in the "spv" name space, e.g.: spv::SourceLanguageGLSL
|
||||
// - C++11 will use enum classes in the spv namespace, e.g.: spv::SourceLanguage::GLSL
|
||||
// - Lua will use tables, e.g.: spv.SourceLanguage.GLSL
|
||||
// - Python will use dictionaries, e.g.: spv['SourceLanguage']['GLSL']
|
||||
// - C# will use enum classes in the Specification class located in the "Spv" namespace,
|
||||
// e.g.: Spv.Specification.SourceLanguage.GLSL
|
||||
// - D will have tokens under the "spv" module, e.g: spv.SourceLanguage.GLSL
|
||||
//
|
||||
// Some tokens act like mask values, which can be OR'd together,
|
||||
// while others are mutually exclusive. The mask-like ones have
|
||||
// "Mask" in their name, and a parallel enum that has the shift
|
||||
// amount (1 << x) for each corresponding enumerant.
|
||||
|
||||
#ifndef spirv_HPP
|
||||
#define spirv_HPP
|
||||
|
||||
namespace spv {
|
||||
|
||||
typedef unsigned int Id;
|
||||
|
||||
#define SPV_VERSION 0x10400
|
||||
#define SPV_REVISION 1
|
||||
|
||||
static const unsigned int MagicNumber = 0x07230203;
|
||||
static const unsigned int Version = 0x00010400;
|
||||
static const unsigned int Revision = 1;
|
||||
static const unsigned int OpCodeMask = 0xffff;
|
||||
static const unsigned int WordCountShift = 16;
|
||||
|
||||
enum SourceLanguage {
|
||||
SourceLanguageUnknown = 0,
|
||||
SourceLanguageESSL = 1,
|
||||
SourceLanguageGLSL = 2,
|
||||
SourceLanguageOpenCL_C = 3,
|
||||
SourceLanguageOpenCL_CPP = 4,
|
||||
SourceLanguageHLSL = 5,
|
||||
SourceLanguageMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum ExecutionModel {
|
||||
ExecutionModelVertex = 0,
|
||||
ExecutionModelTessellationControl = 1,
|
||||
ExecutionModelTessellationEvaluation = 2,
|
||||
ExecutionModelGeometry = 3,
|
||||
ExecutionModelFragment = 4,
|
||||
ExecutionModelGLCompute = 5,
|
||||
ExecutionModelKernel = 6,
|
||||
ExecutionModelTaskNV = 5267,
|
||||
ExecutionModelMeshNV = 5268,
|
||||
ExecutionModelRayGenerationNV = 5313,
|
||||
ExecutionModelIntersectionNV = 5314,
|
||||
ExecutionModelAnyHitNV = 5315,
|
||||
ExecutionModelClosestHitNV = 5316,
|
||||
ExecutionModelMissNV = 5317,
|
||||
ExecutionModelCallableNV = 5318,
|
||||
ExecutionModelMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum AddressingModel {
|
||||
AddressingModelLogical = 0,
|
||||
AddressingModelPhysical32 = 1,
|
||||
AddressingModelPhysical64 = 2,
|
||||
AddressingModelPhysicalStorageBuffer64EXT = 5348,
|
||||
AddressingModelMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum MemoryModel {
|
||||
MemoryModelSimple = 0,
|
||||
MemoryModelGLSL450 = 1,
|
||||
MemoryModelOpenCL = 2,
|
||||
MemoryModelVulkanKHR = 3,
|
||||
MemoryModelMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum ExecutionMode {
|
||||
ExecutionModeInvocations = 0,
|
||||
ExecutionModeSpacingEqual = 1,
|
||||
ExecutionModeSpacingFractionalEven = 2,
|
||||
ExecutionModeSpacingFractionalOdd = 3,
|
||||
ExecutionModeVertexOrderCw = 4,
|
||||
ExecutionModeVertexOrderCcw = 5,
|
||||
ExecutionModePixelCenterInteger = 6,
|
||||
ExecutionModeOriginUpperLeft = 7,
|
||||
ExecutionModeOriginLowerLeft = 8,
|
||||
ExecutionModeEarlyFragmentTests = 9,
|
||||
ExecutionModePointMode = 10,
|
||||
ExecutionModeXfb = 11,
|
||||
ExecutionModeDepthReplacing = 12,
|
||||
ExecutionModeDepthGreater = 14,
|
||||
ExecutionModeDepthLess = 15,
|
||||
ExecutionModeDepthUnchanged = 16,
|
||||
ExecutionModeLocalSize = 17,
|
||||
ExecutionModeLocalSizeHint = 18,
|
||||
ExecutionModeInputPoints = 19,
|
||||
ExecutionModeInputLines = 20,
|
||||
ExecutionModeInputLinesAdjacency = 21,
|
||||
ExecutionModeTriangles = 22,
|
||||
ExecutionModeInputTrianglesAdjacency = 23,
|
||||
ExecutionModeQuads = 24,
|
||||
ExecutionModeIsolines = 25,
|
||||
ExecutionModeOutputVertices = 26,
|
||||
ExecutionModeOutputPoints = 27,
|
||||
ExecutionModeOutputLineStrip = 28,
|
||||
ExecutionModeOutputTriangleStrip = 29,
|
||||
ExecutionModeVecTypeHint = 30,
|
||||
ExecutionModeContractionOff = 31,
|
||||
ExecutionModeInitializer = 33,
|
||||
ExecutionModeFinalizer = 34,
|
||||
ExecutionModeSubgroupSize = 35,
|
||||
ExecutionModeSubgroupsPerWorkgroup = 36,
|
||||
ExecutionModeSubgroupsPerWorkgroupId = 37,
|
||||
ExecutionModeLocalSizeId = 38,
|
||||
ExecutionModeLocalSizeHintId = 39,
|
||||
ExecutionModePostDepthCoverage = 4446,
|
||||
ExecutionModeDenormPreserve = 4459,
|
||||
ExecutionModeDenormFlushToZero = 4460,
|
||||
ExecutionModeSignedZeroInfNanPreserve = 4461,
|
||||
ExecutionModeRoundingModeRTE = 4462,
|
||||
ExecutionModeRoundingModeRTZ = 4463,
|
||||
ExecutionModeStencilRefReplacingEXT = 5027,
|
||||
ExecutionModeOutputLinesNV = 5269,
|
||||
ExecutionModeOutputPrimitivesNV = 5270,
|
||||
ExecutionModeDerivativeGroupQuadsNV = 5289,
|
||||
ExecutionModeDerivativeGroupLinearNV = 5290,
|
||||
ExecutionModeOutputTrianglesNV = 5298,
|
||||
ExecutionModePixelInterlockOrderedEXT = 5366,
|
||||
ExecutionModePixelInterlockUnorderedEXT = 5367,
|
||||
ExecutionModeSampleInterlockOrderedEXT = 5368,
|
||||
ExecutionModeSampleInterlockUnorderedEXT = 5369,
|
||||
ExecutionModeShadingRateInterlockOrderedEXT = 5370,
|
||||
ExecutionModeShadingRateInterlockUnorderedEXT = 5371,
|
||||
ExecutionModeMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum StorageClass {
|
||||
StorageClassUniformConstant = 0,
|
||||
StorageClassInput = 1,
|
||||
StorageClassUniform = 2,
|
||||
StorageClassOutput = 3,
|
||||
StorageClassWorkgroup = 4,
|
||||
StorageClassCrossWorkgroup = 5,
|
||||
StorageClassPrivate = 6,
|
||||
StorageClassFunction = 7,
|
||||
StorageClassGeneric = 8,
|
||||
StorageClassPushConstant = 9,
|
||||
StorageClassAtomicCounter = 10,
|
||||
StorageClassImage = 11,
|
||||
StorageClassStorageBuffer = 12,
|
||||
StorageClassCallableDataNV = 5328,
|
||||
StorageClassIncomingCallableDataNV = 5329,
|
||||
StorageClassRayPayloadNV = 5338,
|
||||
StorageClassHitAttributeNV = 5339,
|
||||
StorageClassIncomingRayPayloadNV = 5342,
|
||||
StorageClassShaderRecordBufferNV = 5343,
|
||||
StorageClassPhysicalStorageBufferEXT = 5349,
|
||||
StorageClassMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum Dim {
|
||||
Dim1D = 0,
|
||||
Dim2D = 1,
|
||||
Dim3D = 2,
|
||||
DimCube = 3,
|
||||
DimRect = 4,
|
||||
DimBuffer = 5,
|
||||
DimSubpassData = 6,
|
||||
DimMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum SamplerAddressingMode {
|
||||
SamplerAddressingModeNone = 0,
|
||||
SamplerAddressingModeClampToEdge = 1,
|
||||
SamplerAddressingModeClamp = 2,
|
||||
SamplerAddressingModeRepeat = 3,
|
||||
SamplerAddressingModeRepeatMirrored = 4,
|
||||
SamplerAddressingModeMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum SamplerFilterMode {
|
||||
SamplerFilterModeNearest = 0,
|
||||
SamplerFilterModeLinear = 1,
|
||||
SamplerFilterModeMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum ImageFormat {
|
||||
ImageFormatUnknown = 0,
|
||||
ImageFormatRgba32f = 1,
|
||||
ImageFormatRgba16f = 2,
|
||||
ImageFormatR32f = 3,
|
||||
ImageFormatRgba8 = 4,
|
||||
ImageFormatRgba8Snorm = 5,
|
||||
ImageFormatRg32f = 6,
|
||||
ImageFormatRg16f = 7,
|
||||
ImageFormatR11fG11fB10f = 8,
|
||||
ImageFormatR16f = 9,
|
||||
ImageFormatRgba16 = 10,
|
||||
ImageFormatRgb10A2 = 11,
|
||||
ImageFormatRg16 = 12,
|
||||
ImageFormatRg8 = 13,
|
||||
ImageFormatR16 = 14,
|
||||
ImageFormatR8 = 15,
|
||||
ImageFormatRgba16Snorm = 16,
|
||||
ImageFormatRg16Snorm = 17,
|
||||
ImageFormatRg8Snorm = 18,
|
||||
ImageFormatR16Snorm = 19,
|
||||
ImageFormatR8Snorm = 20,
|
||||
ImageFormatRgba32i = 21,
|
||||
ImageFormatRgba16i = 22,
|
||||
ImageFormatRgba8i = 23,
|
||||
ImageFormatR32i = 24,
|
||||
ImageFormatRg32i = 25,
|
||||
ImageFormatRg16i = 26,
|
||||
ImageFormatRg8i = 27,
|
||||
ImageFormatR16i = 28,
|
||||
ImageFormatR8i = 29,
|
||||
ImageFormatRgba32ui = 30,
|
||||
ImageFormatRgba16ui = 31,
|
||||
ImageFormatRgba8ui = 32,
|
||||
ImageFormatR32ui = 33,
|
||||
ImageFormatRgb10a2ui = 34,
|
||||
ImageFormatRg32ui = 35,
|
||||
ImageFormatRg16ui = 36,
|
||||
ImageFormatRg8ui = 37,
|
||||
ImageFormatR16ui = 38,
|
||||
ImageFormatR8ui = 39,
|
||||
ImageFormatMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum ImageChannelOrder {
|
||||
ImageChannelOrderR = 0,
|
||||
ImageChannelOrderA = 1,
|
||||
ImageChannelOrderRG = 2,
|
||||
ImageChannelOrderRA = 3,
|
||||
ImageChannelOrderRGB = 4,
|
||||
ImageChannelOrderRGBA = 5,
|
||||
ImageChannelOrderBGRA = 6,
|
||||
ImageChannelOrderARGB = 7,
|
||||
ImageChannelOrderIntensity = 8,
|
||||
ImageChannelOrderLuminance = 9,
|
||||
ImageChannelOrderRx = 10,
|
||||
ImageChannelOrderRGx = 11,
|
||||
ImageChannelOrderRGBx = 12,
|
||||
ImageChannelOrderDepth = 13,
|
||||
ImageChannelOrderDepthStencil = 14,
|
||||
ImageChannelOrdersRGB = 15,
|
||||
ImageChannelOrdersRGBx = 16,
|
||||
ImageChannelOrdersRGBA = 17,
|
||||
ImageChannelOrdersBGRA = 18,
|
||||
ImageChannelOrderABGR = 19,
|
||||
ImageChannelOrderMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum ImageChannelDataType {
|
||||
ImageChannelDataTypeSnormInt8 = 0,
|
||||
ImageChannelDataTypeSnormInt16 = 1,
|
||||
ImageChannelDataTypeUnormInt8 = 2,
|
||||
ImageChannelDataTypeUnormInt16 = 3,
|
||||
ImageChannelDataTypeUnormShort565 = 4,
|
||||
ImageChannelDataTypeUnormShort555 = 5,
|
||||
ImageChannelDataTypeUnormInt101010 = 6,
|
||||
ImageChannelDataTypeSignedInt8 = 7,
|
||||
ImageChannelDataTypeSignedInt16 = 8,
|
||||
ImageChannelDataTypeSignedInt32 = 9,
|
||||
ImageChannelDataTypeUnsignedInt8 = 10,
|
||||
ImageChannelDataTypeUnsignedInt16 = 11,
|
||||
ImageChannelDataTypeUnsignedInt32 = 12,
|
||||
ImageChannelDataTypeHalfFloat = 13,
|
||||
ImageChannelDataTypeFloat = 14,
|
||||
ImageChannelDataTypeUnormInt24 = 15,
|
||||
ImageChannelDataTypeUnormInt101010_2 = 16,
|
||||
ImageChannelDataTypeMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum ImageOperandsShift {
|
||||
ImageOperandsBiasShift = 0,
|
||||
ImageOperandsLodShift = 1,
|
||||
ImageOperandsGradShift = 2,
|
||||
ImageOperandsConstOffsetShift = 3,
|
||||
ImageOperandsOffsetShift = 4,
|
||||
ImageOperandsConstOffsetsShift = 5,
|
||||
ImageOperandsSampleShift = 6,
|
||||
ImageOperandsMinLodShift = 7,
|
||||
ImageOperandsMakeTexelAvailableKHRShift = 8,
|
||||
ImageOperandsMakeTexelVisibleKHRShift = 9,
|
||||
ImageOperandsNonPrivateTexelKHRShift = 10,
|
||||
ImageOperandsVolatileTexelKHRShift = 11,
|
||||
ImageOperandsSignExtendShift = 12,
|
||||
ImageOperandsZeroExtendShift = 13,
|
||||
ImageOperandsMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum ImageOperandsMask {
|
||||
ImageOperandsMaskNone = 0,
|
||||
ImageOperandsBiasMask = 0x00000001,
|
||||
ImageOperandsLodMask = 0x00000002,
|
||||
ImageOperandsGradMask = 0x00000004,
|
||||
ImageOperandsConstOffsetMask = 0x00000008,
|
||||
ImageOperandsOffsetMask = 0x00000010,
|
||||
ImageOperandsConstOffsetsMask = 0x00000020,
|
||||
ImageOperandsSampleMask = 0x00000040,
|
||||
ImageOperandsMinLodMask = 0x00000080,
|
||||
ImageOperandsMakeTexelAvailableKHRMask = 0x00000100,
|
||||
ImageOperandsMakeTexelVisibleKHRMask = 0x00000200,
|
||||
ImageOperandsNonPrivateTexelKHRMask = 0x00000400,
|
||||
ImageOperandsVolatileTexelKHRMask = 0x00000800,
|
||||
ImageOperandsSignExtendMask = 0x00001000,
|
||||
ImageOperandsZeroExtendMask = 0x00002000,
|
||||
};
|
||||
|
||||
enum FPFastMathModeShift {
|
||||
FPFastMathModeNotNaNShift = 0,
|
||||
FPFastMathModeNotInfShift = 1,
|
||||
FPFastMathModeNSZShift = 2,
|
||||
FPFastMathModeAllowRecipShift = 3,
|
||||
FPFastMathModeFastShift = 4,
|
||||
FPFastMathModeMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum FPFastMathModeMask {
|
||||
FPFastMathModeMaskNone = 0,
|
||||
FPFastMathModeNotNaNMask = 0x00000001,
|
||||
FPFastMathModeNotInfMask = 0x00000002,
|
||||
FPFastMathModeNSZMask = 0x00000004,
|
||||
FPFastMathModeAllowRecipMask = 0x00000008,
|
||||
FPFastMathModeFastMask = 0x00000010,
|
||||
};
|
||||
|
||||
enum FPRoundingMode {
|
||||
FPRoundingModeRTE = 0,
|
||||
FPRoundingModeRTZ = 1,
|
||||
FPRoundingModeRTP = 2,
|
||||
FPRoundingModeRTN = 3,
|
||||
FPRoundingModeMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum LinkageType {
|
||||
LinkageTypeExport = 0,
|
||||
LinkageTypeImport = 1,
|
||||
LinkageTypeMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum AccessQualifier {
|
||||
AccessQualifierReadOnly = 0,
|
||||
AccessQualifierWriteOnly = 1,
|
||||
AccessQualifierReadWrite = 2,
|
||||
AccessQualifierMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum FunctionParameterAttribute {
|
||||
FunctionParameterAttributeZext = 0,
|
||||
FunctionParameterAttributeSext = 1,
|
||||
FunctionParameterAttributeByVal = 2,
|
||||
FunctionParameterAttributeSret = 3,
|
||||
FunctionParameterAttributeNoAlias = 4,
|
||||
FunctionParameterAttributeNoCapture = 5,
|
||||
FunctionParameterAttributeNoWrite = 6,
|
||||
FunctionParameterAttributeNoReadWrite = 7,
|
||||
FunctionParameterAttributeMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum Decoration {
|
||||
DecorationRelaxedPrecision = 0,
|
||||
DecorationSpecId = 1,
|
||||
DecorationBlock = 2,
|
||||
DecorationBufferBlock = 3,
|
||||
DecorationRowMajor = 4,
|
||||
DecorationColMajor = 5,
|
||||
DecorationArrayStride = 6,
|
||||
DecorationMatrixStride = 7,
|
||||
DecorationGLSLShared = 8,
|
||||
DecorationGLSLPacked = 9,
|
||||
DecorationCPacked = 10,
|
||||
DecorationBuiltIn = 11,
|
||||
DecorationNoPerspective = 13,
|
||||
DecorationFlat = 14,
|
||||
DecorationPatch = 15,
|
||||
DecorationCentroid = 16,
|
||||
DecorationSample = 17,
|
||||
DecorationInvariant = 18,
|
||||
DecorationRestrict = 19,
|
||||
DecorationAliased = 20,
|
||||
DecorationVolatile = 21,
|
||||
DecorationConstant = 22,
|
||||
DecorationCoherent = 23,
|
||||
DecorationNonWritable = 24,
|
||||
DecorationNonReadable = 25,
|
||||
DecorationUniform = 26,
|
||||
DecorationUniformId = 27,
|
||||
DecorationSaturatedConversion = 28,
|
||||
DecorationStream = 29,
|
||||
DecorationLocation = 30,
|
||||
DecorationComponent = 31,
|
||||
DecorationIndex = 32,
|
||||
DecorationBinding = 33,
|
||||
DecorationDescriptorSet = 34,
|
||||
DecorationOffset = 35,
|
||||
DecorationXfbBuffer = 36,
|
||||
DecorationXfbStride = 37,
|
||||
DecorationFuncParamAttr = 38,
|
||||
DecorationFPRoundingMode = 39,
|
||||
DecorationFPFastMathMode = 40,
|
||||
DecorationLinkageAttributes = 41,
|
||||
DecorationNoContraction = 42,
|
||||
DecorationInputAttachmentIndex = 43,
|
||||
DecorationAlignment = 44,
|
||||
DecorationMaxByteOffset = 45,
|
||||
DecorationAlignmentId = 46,
|
||||
DecorationMaxByteOffsetId = 47,
|
||||
DecorationNoSignedWrap = 4469,
|
||||
DecorationNoUnsignedWrap = 4470,
|
||||
DecorationExplicitInterpAMD = 4999,
|
||||
DecorationOverrideCoverageNV = 5248,
|
||||
DecorationPassthroughNV = 5250,
|
||||
DecorationViewportRelativeNV = 5252,
|
||||
DecorationSecondaryViewportRelativeNV = 5256,
|
||||
DecorationPerPrimitiveNV = 5271,
|
||||
DecorationPerViewNV = 5272,
|
||||
DecorationPerTaskNV = 5273,
|
||||
DecorationPerVertexNV = 5285,
|
||||
DecorationNonUniformEXT = 5300,
|
||||
DecorationRestrictPointerEXT = 5355,
|
||||
DecorationAliasedPointerEXT = 5356,
|
||||
DecorationCounterBuffer = 5634,
|
||||
DecorationHlslCounterBufferGOOGLE = 5634,
|
||||
DecorationHlslSemanticGOOGLE = 5635,
|
||||
DecorationUserSemantic = 5635,
|
||||
DecorationUserTypeGOOGLE = 5636,
|
||||
DecorationMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum BuiltIn {
|
||||
BuiltInPosition = 0,
|
||||
BuiltInPointSize = 1,
|
||||
BuiltInClipDistance = 3,
|
||||
BuiltInCullDistance = 4,
|
||||
BuiltInVertexId = 5,
|
||||
BuiltInInstanceId = 6,
|
||||
BuiltInPrimitiveId = 7,
|
||||
BuiltInInvocationId = 8,
|
||||
BuiltInLayer = 9,
|
||||
BuiltInViewportIndex = 10,
|
||||
BuiltInTessLevelOuter = 11,
|
||||
BuiltInTessLevelInner = 12,
|
||||
BuiltInTessCoord = 13,
|
||||
BuiltInPatchVertices = 14,
|
||||
BuiltInFragCoord = 15,
|
||||
BuiltInPointCoord = 16,
|
||||
BuiltInFrontFacing = 17,
|
||||
BuiltInSampleId = 18,
|
||||
BuiltInSamplePosition = 19,
|
||||
BuiltInSampleMask = 20,
|
||||
BuiltInFragDepth = 22,
|
||||
BuiltInHelperInvocation = 23,
|
||||
BuiltInNumWorkgroups = 24,
|
||||
BuiltInWorkgroupSize = 25,
|
||||
BuiltInWorkgroupId = 26,
|
||||
BuiltInLocalInvocationId = 27,
|
||||
BuiltInGlobalInvocationId = 28,
|
||||
BuiltInLocalInvocationIndex = 29,
|
||||
BuiltInWorkDim = 30,
|
||||
BuiltInGlobalSize = 31,
|
||||
BuiltInEnqueuedWorkgroupSize = 32,
|
||||
BuiltInGlobalOffset = 33,
|
||||
BuiltInGlobalLinearId = 34,
|
||||
BuiltInSubgroupSize = 36,
|
||||
BuiltInSubgroupMaxSize = 37,
|
||||
BuiltInNumSubgroups = 38,
|
||||
BuiltInNumEnqueuedSubgroups = 39,
|
||||
BuiltInSubgroupId = 40,
|
||||
BuiltInSubgroupLocalInvocationId = 41,
|
||||
BuiltInVertexIndex = 42,
|
||||
BuiltInInstanceIndex = 43,
|
||||
BuiltInSubgroupEqMask = 4416,
|
||||
BuiltInSubgroupEqMaskKHR = 4416,
|
||||
BuiltInSubgroupGeMask = 4417,
|
||||
BuiltInSubgroupGeMaskKHR = 4417,
|
||||
BuiltInSubgroupGtMask = 4418,
|
||||
BuiltInSubgroupGtMaskKHR = 4418,
|
||||
BuiltInSubgroupLeMask = 4419,
|
||||
BuiltInSubgroupLeMaskKHR = 4419,
|
||||
BuiltInSubgroupLtMask = 4420,
|
||||
BuiltInSubgroupLtMaskKHR = 4420,
|
||||
BuiltInBaseVertex = 4424,
|
||||
BuiltInBaseInstance = 4425,
|
||||
BuiltInDrawIndex = 4426,
|
||||
BuiltInDeviceIndex = 4438,
|
||||
BuiltInViewIndex = 4440,
|
||||
BuiltInBaryCoordNoPerspAMD = 4992,
|
||||
BuiltInBaryCoordNoPerspCentroidAMD = 4993,
|
||||
BuiltInBaryCoordNoPerspSampleAMD = 4994,
|
||||
BuiltInBaryCoordSmoothAMD = 4995,
|
||||
BuiltInBaryCoordSmoothCentroidAMD = 4996,
|
||||
BuiltInBaryCoordSmoothSampleAMD = 4997,
|
||||
BuiltInBaryCoordPullModelAMD = 4998,
|
||||
BuiltInFragStencilRefEXT = 5014,
|
||||
BuiltInViewportMaskNV = 5253,
|
||||
BuiltInSecondaryPositionNV = 5257,
|
||||
BuiltInSecondaryViewportMaskNV = 5258,
|
||||
BuiltInPositionPerViewNV = 5261,
|
||||
BuiltInViewportMaskPerViewNV = 5262,
|
||||
BuiltInFullyCoveredEXT = 5264,
|
||||
BuiltInTaskCountNV = 5274,
|
||||
BuiltInPrimitiveCountNV = 5275,
|
||||
BuiltInPrimitiveIndicesNV = 5276,
|
||||
BuiltInClipDistancePerViewNV = 5277,
|
||||
BuiltInCullDistancePerViewNV = 5278,
|
||||
BuiltInLayerPerViewNV = 5279,
|
||||
BuiltInMeshViewCountNV = 5280,
|
||||
BuiltInMeshViewIndicesNV = 5281,
|
||||
BuiltInBaryCoordNV = 5286,
|
||||
BuiltInBaryCoordNoPerspNV = 5287,
|
||||
BuiltInFragSizeEXT = 5292,
|
||||
BuiltInFragmentSizeNV = 5292,
|
||||
BuiltInFragInvocationCountEXT = 5293,
|
||||
BuiltInInvocationsPerPixelNV = 5293,
|
||||
BuiltInLaunchIdNV = 5319,
|
||||
BuiltInLaunchSizeNV = 5320,
|
||||
BuiltInWorldRayOriginNV = 5321,
|
||||
BuiltInWorldRayDirectionNV = 5322,
|
||||
BuiltInObjectRayOriginNV = 5323,
|
||||
BuiltInObjectRayDirectionNV = 5324,
|
||||
BuiltInRayTminNV = 5325,
|
||||
BuiltInRayTmaxNV = 5326,
|
||||
BuiltInInstanceCustomIndexNV = 5327,
|
||||
BuiltInObjectToWorldNV = 5330,
|
||||
BuiltInWorldToObjectNV = 5331,
|
||||
BuiltInHitTNV = 5332,
|
||||
BuiltInHitKindNV = 5333,
|
||||
BuiltInIncomingRayFlagsNV = 5351,
|
||||
BuiltInWarpsPerSMNV = 5374,
|
||||
BuiltInSMCountNV = 5375,
|
||||
BuiltInWarpIDNV = 5376,
|
||||
BuiltInSMIDNV = 5377,
|
||||
BuiltInMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum SelectionControlShift {
|
||||
SelectionControlFlattenShift = 0,
|
||||
SelectionControlDontFlattenShift = 1,
|
||||
SelectionControlMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum SelectionControlMask {
|
||||
SelectionControlMaskNone = 0,
|
||||
SelectionControlFlattenMask = 0x00000001,
|
||||
SelectionControlDontFlattenMask = 0x00000002,
|
||||
};
|
||||
|
||||
enum LoopControlShift {
|
||||
LoopControlUnrollShift = 0,
|
||||
LoopControlDontUnrollShift = 1,
|
||||
LoopControlDependencyInfiniteShift = 2,
|
||||
LoopControlDependencyLengthShift = 3,
|
||||
LoopControlMinIterationsShift = 4,
|
||||
LoopControlMaxIterationsShift = 5,
|
||||
LoopControlIterationMultipleShift = 6,
|
||||
LoopControlPeelCountShift = 7,
|
||||
LoopControlPartialCountShift = 8,
|
||||
LoopControlMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum LoopControlMask {
|
||||
LoopControlMaskNone = 0,
|
||||
LoopControlUnrollMask = 0x00000001,
|
||||
LoopControlDontUnrollMask = 0x00000002,
|
||||
LoopControlDependencyInfiniteMask = 0x00000004,
|
||||
LoopControlDependencyLengthMask = 0x00000008,
|
||||
LoopControlMinIterationsMask = 0x00000010,
|
||||
LoopControlMaxIterationsMask = 0x00000020,
|
||||
LoopControlIterationMultipleMask = 0x00000040,
|
||||
LoopControlPeelCountMask = 0x00000080,
|
||||
LoopControlPartialCountMask = 0x00000100,
|
||||
};
|
||||
|
||||
enum FunctionControlShift {
|
||||
FunctionControlInlineShift = 0,
|
||||
FunctionControlDontInlineShift = 1,
|
||||
FunctionControlPureShift = 2,
|
||||
FunctionControlConstShift = 3,
|
||||
FunctionControlMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum FunctionControlMask {
|
||||
FunctionControlMaskNone = 0,
|
||||
FunctionControlInlineMask = 0x00000001,
|
||||
FunctionControlDontInlineMask = 0x00000002,
|
||||
FunctionControlPureMask = 0x00000004,
|
||||
FunctionControlConstMask = 0x00000008,
|
||||
};
|
||||
|
||||
enum MemorySemanticsShift {
|
||||
MemorySemanticsAcquireShift = 1,
|
||||
MemorySemanticsReleaseShift = 2,
|
||||
MemorySemanticsAcquireReleaseShift = 3,
|
||||
MemorySemanticsSequentiallyConsistentShift = 4,
|
||||
MemorySemanticsUniformMemoryShift = 6,
|
||||
MemorySemanticsSubgroupMemoryShift = 7,
|
||||
MemorySemanticsWorkgroupMemoryShift = 8,
|
||||
MemorySemanticsCrossWorkgroupMemoryShift = 9,
|
||||
MemorySemanticsAtomicCounterMemoryShift = 10,
|
||||
MemorySemanticsImageMemoryShift = 11,
|
||||
MemorySemanticsOutputMemoryKHRShift = 12,
|
||||
MemorySemanticsMakeAvailableKHRShift = 13,
|
||||
MemorySemanticsMakeVisibleKHRShift = 14,
|
||||
MemorySemanticsVolatileShift = 15,
|
||||
MemorySemanticsMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum MemorySemanticsMask {
|
||||
MemorySemanticsMaskNone = 0,
|
||||
MemorySemanticsAcquireMask = 0x00000002,
|
||||
MemorySemanticsReleaseMask = 0x00000004,
|
||||
MemorySemanticsAcquireReleaseMask = 0x00000008,
|
||||
MemorySemanticsSequentiallyConsistentMask = 0x00000010,
|
||||
MemorySemanticsUniformMemoryMask = 0x00000040,
|
||||
MemorySemanticsSubgroupMemoryMask = 0x00000080,
|
||||
MemorySemanticsWorkgroupMemoryMask = 0x00000100,
|
||||
MemorySemanticsCrossWorkgroupMemoryMask = 0x00000200,
|
||||
MemorySemanticsAtomicCounterMemoryMask = 0x00000400,
|
||||
MemorySemanticsImageMemoryMask = 0x00000800,
|
||||
MemorySemanticsOutputMemoryKHRMask = 0x00001000,
|
||||
MemorySemanticsMakeAvailableKHRMask = 0x00002000,
|
||||
MemorySemanticsMakeVisibleKHRMask = 0x00004000,
|
||||
MemorySemanticsVolatileMask = 0x00008000,
|
||||
};
|
||||
|
||||
enum MemoryAccessShift {
|
||||
MemoryAccessVolatileShift = 0,
|
||||
MemoryAccessAlignedShift = 1,
|
||||
MemoryAccessNontemporalShift = 2,
|
||||
MemoryAccessMakePointerAvailableKHRShift = 3,
|
||||
MemoryAccessMakePointerVisibleKHRShift = 4,
|
||||
MemoryAccessNonPrivatePointerKHRShift = 5,
|
||||
MemoryAccessMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum MemoryAccessMask {
|
||||
MemoryAccessMaskNone = 0,
|
||||
MemoryAccessVolatileMask = 0x00000001,
|
||||
MemoryAccessAlignedMask = 0x00000002,
|
||||
MemoryAccessNontemporalMask = 0x00000004,
|
||||
MemoryAccessMakePointerAvailableKHRMask = 0x00000008,
|
||||
MemoryAccessMakePointerVisibleKHRMask = 0x00000010,
|
||||
MemoryAccessNonPrivatePointerKHRMask = 0x00000020,
|
||||
};
|
||||
|
||||
enum Scope {
|
||||
ScopeCrossDevice = 0,
|
||||
ScopeDevice = 1,
|
||||
ScopeWorkgroup = 2,
|
||||
ScopeSubgroup = 3,
|
||||
ScopeInvocation = 4,
|
||||
ScopeQueueFamilyKHR = 5,
|
||||
ScopeMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum GroupOperation {
|
||||
GroupOperationReduce = 0,
|
||||
GroupOperationInclusiveScan = 1,
|
||||
GroupOperationExclusiveScan = 2,
|
||||
GroupOperationClusteredReduce = 3,
|
||||
GroupOperationPartitionedReduceNV = 6,
|
||||
GroupOperationPartitionedInclusiveScanNV = 7,
|
||||
GroupOperationPartitionedExclusiveScanNV = 8,
|
||||
GroupOperationMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum KernelEnqueueFlags {
|
||||
KernelEnqueueFlagsNoWait = 0,
|
||||
KernelEnqueueFlagsWaitKernel = 1,
|
||||
KernelEnqueueFlagsWaitWorkGroup = 2,
|
||||
KernelEnqueueFlagsMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum KernelProfilingInfoShift {
|
||||
KernelProfilingInfoCmdExecTimeShift = 0,
|
||||
KernelProfilingInfoMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum KernelProfilingInfoMask {
|
||||
KernelProfilingInfoMaskNone = 0,
|
||||
KernelProfilingInfoCmdExecTimeMask = 0x00000001,
|
||||
};
|
||||
|
||||
enum Capability {
|
||||
CapabilityMatrix = 0,
|
||||
CapabilityShader = 1,
|
||||
CapabilityGeometry = 2,
|
||||
CapabilityTessellation = 3,
|
||||
CapabilityAddresses = 4,
|
||||
CapabilityLinkage = 5,
|
||||
CapabilityKernel = 6,
|
||||
CapabilityVector16 = 7,
|
||||
CapabilityFloat16Buffer = 8,
|
||||
CapabilityFloat16 = 9,
|
||||
CapabilityFloat64 = 10,
|
||||
CapabilityInt64 = 11,
|
||||
CapabilityInt64Atomics = 12,
|
||||
CapabilityImageBasic = 13,
|
||||
CapabilityImageReadWrite = 14,
|
||||
CapabilityImageMipmap = 15,
|
||||
CapabilityPipes = 17,
|
||||
CapabilityGroups = 18,
|
||||
CapabilityDeviceEnqueue = 19,
|
||||
CapabilityLiteralSampler = 20,
|
||||
CapabilityAtomicStorage = 21,
|
||||
CapabilityInt16 = 22,
|
||||
CapabilityTessellationPointSize = 23,
|
||||
CapabilityGeometryPointSize = 24,
|
||||
CapabilityImageGatherExtended = 25,
|
||||
CapabilityStorageImageMultisample = 27,
|
||||
CapabilityUniformBufferArrayDynamicIndexing = 28,
|
||||
CapabilitySampledImageArrayDynamicIndexing = 29,
|
||||
CapabilityStorageBufferArrayDynamicIndexing = 30,
|
||||
CapabilityStorageImageArrayDynamicIndexing = 31,
|
||||
CapabilityClipDistance = 32,
|
||||
CapabilityCullDistance = 33,
|
||||
CapabilityImageCubeArray = 34,
|
||||
CapabilitySampleRateShading = 35,
|
||||
CapabilityImageRect = 36,
|
||||
CapabilitySampledRect = 37,
|
||||
CapabilityGenericPointer = 38,
|
||||
CapabilityInt8 = 39,
|
||||
CapabilityInputAttachment = 40,
|
||||
CapabilitySparseResidency = 41,
|
||||
CapabilityMinLod = 42,
|
||||
CapabilitySampled1D = 43,
|
||||
CapabilityImage1D = 44,
|
||||
CapabilitySampledCubeArray = 45,
|
||||
CapabilitySampledBuffer = 46,
|
||||
CapabilityImageBuffer = 47,
|
||||
CapabilityImageMSArray = 48,
|
||||
CapabilityStorageImageExtendedFormats = 49,
|
||||
CapabilityImageQuery = 50,
|
||||
CapabilityDerivativeControl = 51,
|
||||
CapabilityInterpolationFunction = 52,
|
||||
CapabilityTransformFeedback = 53,
|
||||
CapabilityGeometryStreams = 54,
|
||||
CapabilityStorageImageReadWithoutFormat = 55,
|
||||
CapabilityStorageImageWriteWithoutFormat = 56,
|
||||
CapabilityMultiViewport = 57,
|
||||
CapabilitySubgroupDispatch = 58,
|
||||
CapabilityNamedBarrier = 59,
|
||||
CapabilityPipeStorage = 60,
|
||||
CapabilityGroupNonUniform = 61,
|
||||
CapabilityGroupNonUniformVote = 62,
|
||||
CapabilityGroupNonUniformArithmetic = 63,
|
||||
CapabilityGroupNonUniformBallot = 64,
|
||||
CapabilityGroupNonUniformShuffle = 65,
|
||||
CapabilityGroupNonUniformShuffleRelative = 66,
|
||||
CapabilityGroupNonUniformClustered = 67,
|
||||
CapabilityGroupNonUniformQuad = 68,
|
||||
CapabilitySubgroupBallotKHR = 4423,
|
||||
CapabilityDrawParameters = 4427,
|
||||
CapabilitySubgroupVoteKHR = 4431,
|
||||
CapabilityStorageBuffer16BitAccess = 4433,
|
||||
CapabilityStorageUniformBufferBlock16 = 4433,
|
||||
CapabilityStorageUniform16 = 4434,
|
||||
CapabilityUniformAndStorageBuffer16BitAccess = 4434,
|
||||
CapabilityStoragePushConstant16 = 4435,
|
||||
CapabilityStorageInputOutput16 = 4436,
|
||||
CapabilityDeviceGroup = 4437,
|
||||
CapabilityMultiView = 4439,
|
||||
CapabilityVariablePointersStorageBuffer = 4441,
|
||||
CapabilityVariablePointers = 4442,
|
||||
CapabilityAtomicStorageOps = 4445,
|
||||
CapabilitySampleMaskPostDepthCoverage = 4447,
|
||||
CapabilityStorageBuffer8BitAccess = 4448,
|
||||
CapabilityUniformAndStorageBuffer8BitAccess = 4449,
|
||||
CapabilityStoragePushConstant8 = 4450,
|
||||
CapabilityDenormPreserve = 4464,
|
||||
CapabilityDenormFlushToZero = 4465,
|
||||
CapabilitySignedZeroInfNanPreserve = 4466,
|
||||
CapabilityRoundingModeRTE = 4467,
|
||||
CapabilityRoundingModeRTZ = 4468,
|
||||
CapabilityFloat16ImageAMD = 5008,
|
||||
CapabilityImageGatherBiasLodAMD = 5009,
|
||||
CapabilityFragmentMaskAMD = 5010,
|
||||
CapabilityStencilExportEXT = 5013,
|
||||
CapabilityImageReadWriteLodAMD = 5015,
|
||||
CapabilitySampleMaskOverrideCoverageNV = 5249,
|
||||
CapabilityGeometryShaderPassthroughNV = 5251,
|
||||
CapabilityShaderViewportIndexLayerEXT = 5254,
|
||||
CapabilityShaderViewportIndexLayerNV = 5254,
|
||||
CapabilityShaderViewportMaskNV = 5255,
|
||||
CapabilityShaderStereoViewNV = 5259,
|
||||
CapabilityPerViewAttributesNV = 5260,
|
||||
CapabilityFragmentFullyCoveredEXT = 5265,
|
||||
CapabilityMeshShadingNV = 5266,
|
||||
CapabilityImageFootprintNV = 5282,
|
||||
CapabilityFragmentBarycentricNV = 5284,
|
||||
CapabilityComputeDerivativeGroupQuadsNV = 5288,
|
||||
CapabilityFragmentDensityEXT = 5291,
|
||||
CapabilityShadingRateNV = 5291,
|
||||
CapabilityGroupNonUniformPartitionedNV = 5297,
|
||||
CapabilityShaderNonUniformEXT = 5301,
|
||||
CapabilityRuntimeDescriptorArrayEXT = 5302,
|
||||
CapabilityInputAttachmentArrayDynamicIndexingEXT = 5303,
|
||||
CapabilityUniformTexelBufferArrayDynamicIndexingEXT = 5304,
|
||||
CapabilityStorageTexelBufferArrayDynamicIndexingEXT = 5305,
|
||||
CapabilityUniformBufferArrayNonUniformIndexingEXT = 5306,
|
||||
CapabilitySampledImageArrayNonUniformIndexingEXT = 5307,
|
||||
CapabilityStorageBufferArrayNonUniformIndexingEXT = 5308,
|
||||
CapabilityStorageImageArrayNonUniformIndexingEXT = 5309,
|
||||
CapabilityInputAttachmentArrayNonUniformIndexingEXT = 5310,
|
||||
CapabilityUniformTexelBufferArrayNonUniformIndexingEXT = 5311,
|
||||
CapabilityStorageTexelBufferArrayNonUniformIndexingEXT = 5312,
|
||||
CapabilityRayTracingNV = 5340,
|
||||
CapabilityVulkanMemoryModelKHR = 5345,
|
||||
CapabilityVulkanMemoryModelDeviceScopeKHR = 5346,
|
||||
CapabilityPhysicalStorageBufferAddressesEXT = 5347,
|
||||
CapabilityComputeDerivativeGroupLinearNV = 5350,
|
||||
CapabilityCooperativeMatrixNV = 5357,
|
||||
CapabilityFragmentShaderSampleInterlockEXT = 5363,
|
||||
CapabilityFragmentShaderShadingRateInterlockEXT = 5372,
|
||||
CapabilityShaderSMBuiltinsNV = 5373,
|
||||
CapabilityFragmentShaderPixelInterlockEXT = 5378,
|
||||
CapabilityDemoteToHelperInvocationEXT = 5379,
|
||||
CapabilitySubgroupShuffleINTEL = 5568,
|
||||
CapabilitySubgroupBufferBlockIOINTEL = 5569,
|
||||
CapabilitySubgroupImageBlockIOINTEL = 5570,
|
||||
CapabilitySubgroupImageMediaBlockIOINTEL = 5579,
|
||||
CapabilityIntegerFunctions2INTEL = 5584,
|
||||
CapabilitySubgroupAvcMotionEstimationINTEL = 5696,
|
||||
CapabilitySubgroupAvcMotionEstimationIntraINTEL = 5697,
|
||||
CapabilitySubgroupAvcMotionEstimationChromaINTEL = 5698,
|
||||
CapabilityMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
enum Op {
|
||||
OpNop = 0,
|
||||
OpUndef = 1,
|
||||
OpSourceContinued = 2,
|
||||
OpSource = 3,
|
||||
OpSourceExtension = 4,
|
||||
OpName = 5,
|
||||
OpMemberName = 6,
|
||||
OpString = 7,
|
||||
OpLine = 8,
|
||||
OpExtension = 10,
|
||||
OpExtInstImport = 11,
|
||||
OpExtInst = 12,
|
||||
OpMemoryModel = 14,
|
||||
OpEntryPoint = 15,
|
||||
OpExecutionMode = 16,
|
||||
OpCapability = 17,
|
||||
OpTypeVoid = 19,
|
||||
OpTypeBool = 20,
|
||||
OpTypeInt = 21,
|
||||
OpTypeFloat = 22,
|
||||
OpTypeVector = 23,
|
||||
OpTypeMatrix = 24,
|
||||
OpTypeImage = 25,
|
||||
OpTypeSampler = 26,
|
||||
OpTypeSampledImage = 27,
|
||||
OpTypeArray = 28,
|
||||
OpTypeRuntimeArray = 29,
|
||||
OpTypeStruct = 30,
|
||||
OpTypeOpaque = 31,
|
||||
OpTypePointer = 32,
|
||||
OpTypeFunction = 33,
|
||||
OpTypeEvent = 34,
|
||||
OpTypeDeviceEvent = 35,
|
||||
OpTypeReserveId = 36,
|
||||
OpTypeQueue = 37,
|
||||
OpTypePipe = 38,
|
||||
OpTypeForwardPointer = 39,
|
||||
OpConstantTrue = 41,
|
||||
OpConstantFalse = 42,
|
||||
OpConstant = 43,
|
||||
OpConstantComposite = 44,
|
||||
OpConstantSampler = 45,
|
||||
OpConstantNull = 46,
|
||||
OpSpecConstantTrue = 48,
|
||||
OpSpecConstantFalse = 49,
|
||||
OpSpecConstant = 50,
|
||||
OpSpecConstantComposite = 51,
|
||||
OpSpecConstantOp = 52,
|
||||
OpFunction = 54,
|
||||
OpFunctionParameter = 55,
|
||||
OpFunctionEnd = 56,
|
||||
OpFunctionCall = 57,
|
||||
OpVariable = 59,
|
||||
OpImageTexelPointer = 60,
|
||||
OpLoad = 61,
|
||||
OpStore = 62,
|
||||
OpCopyMemory = 63,
|
||||
OpCopyMemorySized = 64,
|
||||
OpAccessChain = 65,
|
||||
OpInBoundsAccessChain = 66,
|
||||
OpPtrAccessChain = 67,
|
||||
OpArrayLength = 68,
|
||||
OpGenericPtrMemSemantics = 69,
|
||||
OpInBoundsPtrAccessChain = 70,
|
||||
OpDecorate = 71,
|
||||
OpMemberDecorate = 72,
|
||||
OpDecorationGroup = 73,
|
||||
OpGroupDecorate = 74,
|
||||
OpGroupMemberDecorate = 75,
|
||||
OpVectorExtractDynamic = 77,
|
||||
OpVectorInsertDynamic = 78,
|
||||
OpVectorShuffle = 79,
|
||||
OpCompositeConstruct = 80,
|
||||
OpCompositeExtract = 81,
|
||||
OpCompositeInsert = 82,
|
||||
OpCopyObject = 83,
|
||||
OpTranspose = 84,
|
||||
OpSampledImage = 86,
|
||||
OpImageSampleImplicitLod = 87,
|
||||
OpImageSampleExplicitLod = 88,
|
||||
OpImageSampleDrefImplicitLod = 89,
|
||||
OpImageSampleDrefExplicitLod = 90,
|
||||
OpImageSampleProjImplicitLod = 91,
|
||||
OpImageSampleProjExplicitLod = 92,
|
||||
OpImageSampleProjDrefImplicitLod = 93,
|
||||
OpImageSampleProjDrefExplicitLod = 94,
|
||||
OpImageFetch = 95,
|
||||
OpImageGather = 96,
|
||||
OpImageDrefGather = 97,
|
||||
OpImageRead = 98,
|
||||
OpImageWrite = 99,
|
||||
OpImage = 100,
|
||||
OpImageQueryFormat = 101,
|
||||
OpImageQueryOrder = 102,
|
||||
OpImageQuerySizeLod = 103,
|
||||
OpImageQuerySize = 104,
|
||||
OpImageQueryLod = 105,
|
||||
OpImageQueryLevels = 106,
|
||||
OpImageQuerySamples = 107,
|
||||
OpConvertFToU = 109,
|
||||
OpConvertFToS = 110,
|
||||
OpConvertSToF = 111,
|
||||
OpConvertUToF = 112,
|
||||
OpUConvert = 113,
|
||||
OpSConvert = 114,
|
||||
OpFConvert = 115,
|
||||
OpQuantizeToF16 = 116,
|
||||
OpConvertPtrToU = 117,
|
||||
OpSatConvertSToU = 118,
|
||||
OpSatConvertUToS = 119,
|
||||
OpConvertUToPtr = 120,
|
||||
OpPtrCastToGeneric = 121,
|
||||
OpGenericCastToPtr = 122,
|
||||
OpGenericCastToPtrExplicit = 123,
|
||||
OpBitcast = 124,
|
||||
OpSNegate = 126,
|
||||
OpFNegate = 127,
|
||||
OpIAdd = 128,
|
||||
OpFAdd = 129,
|
||||
OpISub = 130,
|
||||
OpFSub = 131,
|
||||
OpIMul = 132,
|
||||
OpFMul = 133,
|
||||
OpUDiv = 134,
|
||||
OpSDiv = 135,
|
||||
OpFDiv = 136,
|
||||
OpUMod = 137,
|
||||
OpSRem = 138,
|
||||
OpSMod = 139,
|
||||
OpFRem = 140,
|
||||
OpFMod = 141,
|
||||
OpVectorTimesScalar = 142,
|
||||
OpMatrixTimesScalar = 143,
|
||||
OpVectorTimesMatrix = 144,
|
||||
OpMatrixTimesVector = 145,
|
||||
OpMatrixTimesMatrix = 146,
|
||||
OpOuterProduct = 147,
|
||||
OpDot = 148,
|
||||
OpIAddCarry = 149,
|
||||
OpISubBorrow = 150,
|
||||
OpUMulExtended = 151,
|
||||
OpSMulExtended = 152,
|
||||
OpAny = 154,
|
||||
OpAll = 155,
|
||||
OpIsNan = 156,
|
||||
OpIsInf = 157,
|
||||
OpIsFinite = 158,
|
||||
OpIsNormal = 159,
|
||||
OpSignBitSet = 160,
|
||||
OpLessOrGreater = 161,
|
||||
OpOrdered = 162,
|
||||
OpUnordered = 163,
|
||||
OpLogicalEqual = 164,
|
||||
OpLogicalNotEqual = 165,
|
||||
OpLogicalOr = 166,
|
||||
OpLogicalAnd = 167,
|
||||
OpLogicalNot = 168,
|
||||
OpSelect = 169,
|
||||
OpIEqual = 170,
|
||||
OpINotEqual = 171,
|
||||
OpUGreaterThan = 172,
|
||||
OpSGreaterThan = 173,
|
||||
OpUGreaterThanEqual = 174,
|
||||
OpSGreaterThanEqual = 175,
|
||||
OpULessThan = 176,
|
||||
OpSLessThan = 177,
|
||||
OpULessThanEqual = 178,
|
||||
OpSLessThanEqual = 179,
|
||||
OpFOrdEqual = 180,
|
||||
OpFUnordEqual = 181,
|
||||
OpFOrdNotEqual = 182,
|
||||
OpFUnordNotEqual = 183,
|
||||
OpFOrdLessThan = 184,
|
||||
OpFUnordLessThan = 185,
|
||||
OpFOrdGreaterThan = 186,
|
||||
OpFUnordGreaterThan = 187,
|
||||
OpFOrdLessThanEqual = 188,
|
||||
OpFUnordLessThanEqual = 189,
|
||||
OpFOrdGreaterThanEqual = 190,
|
||||
OpFUnordGreaterThanEqual = 191,
|
||||
OpShiftRightLogical = 194,
|
||||
OpShiftRightArithmetic = 195,
|
||||
OpShiftLeftLogical = 196,
|
||||
OpBitwiseOr = 197,
|
||||
OpBitwiseXor = 198,
|
||||
OpBitwiseAnd = 199,
|
||||
OpNot = 200,
|
||||
OpBitFieldInsert = 201,
|
||||
OpBitFieldSExtract = 202,
|
||||
OpBitFieldUExtract = 203,
|
||||
OpBitReverse = 204,
|
||||
OpBitCount = 205,
|
||||
OpDPdx = 207,
|
||||
OpDPdy = 208,
|
||||
OpFwidth = 209,
|
||||
OpDPdxFine = 210,
|
||||
OpDPdyFine = 211,
|
||||
OpFwidthFine = 212,
|
||||
OpDPdxCoarse = 213,
|
||||
OpDPdyCoarse = 214,
|
||||
OpFwidthCoarse = 215,
|
||||
OpEmitVertex = 218,
|
||||
OpEndPrimitive = 219,
|
||||
OpEmitStreamVertex = 220,
|
||||
OpEndStreamPrimitive = 221,
|
||||
OpControlBarrier = 224,
|
||||
OpMemoryBarrier = 225,
|
||||
OpAtomicLoad = 227,
|
||||
OpAtomicStore = 228,
|
||||
OpAtomicExchange = 229,
|
||||
OpAtomicCompareExchange = 230,
|
||||
OpAtomicCompareExchangeWeak = 231,
|
||||
OpAtomicIIncrement = 232,
|
||||
OpAtomicIDecrement = 233,
|
||||
OpAtomicIAdd = 234,
|
||||
OpAtomicISub = 235,
|
||||
OpAtomicSMin = 236,
|
||||
OpAtomicUMin = 237,
|
||||
OpAtomicSMax = 238,
|
||||
OpAtomicUMax = 239,
|
||||
OpAtomicAnd = 240,
|
||||
OpAtomicOr = 241,
|
||||
OpAtomicXor = 242,
|
||||
OpPhi = 245,
|
||||
OpLoopMerge = 246,
|
||||
OpSelectionMerge = 247,
|
||||
OpLabel = 248,
|
||||
OpBranch = 249,
|
||||
OpBranchConditional = 250,
|
||||
OpSwitch = 251,
|
||||
OpKill = 252,
|
||||
OpReturn = 253,
|
||||
OpReturnValue = 254,
|
||||
OpUnreachable = 255,
|
||||
OpLifetimeStart = 256,
|
||||
OpLifetimeStop = 257,
|
||||
OpGroupAsyncCopy = 259,
|
||||
OpGroupWaitEvents = 260,
|
||||
OpGroupAll = 261,
|
||||
OpGroupAny = 262,
|
||||
OpGroupBroadcast = 263,
|
||||
OpGroupIAdd = 264,
|
||||
OpGroupFAdd = 265,
|
||||
OpGroupFMin = 266,
|
||||
OpGroupUMin = 267,
|
||||
OpGroupSMin = 268,
|
||||
OpGroupFMax = 269,
|
||||
OpGroupUMax = 270,
|
||||
OpGroupSMax = 271,
|
||||
OpReadPipe = 274,
|
||||
OpWritePipe = 275,
|
||||
OpReservedReadPipe = 276,
|
||||
OpReservedWritePipe = 277,
|
||||
OpReserveReadPipePackets = 278,
|
||||
OpReserveWritePipePackets = 279,
|
||||
OpCommitReadPipe = 280,
|
||||
OpCommitWritePipe = 281,
|
||||
OpIsValidReserveId = 282,
|
||||
OpGetNumPipePackets = 283,
|
||||
OpGetMaxPipePackets = 284,
|
||||
OpGroupReserveReadPipePackets = 285,
|
||||
OpGroupReserveWritePipePackets = 286,
|
||||
OpGroupCommitReadPipe = 287,
|
||||
OpGroupCommitWritePipe = 288,
|
||||
OpEnqueueMarker = 291,
|
||||
OpEnqueueKernel = 292,
|
||||
OpGetKernelNDrangeSubGroupCount = 293,
|
||||
OpGetKernelNDrangeMaxSubGroupSize = 294,
|
||||
OpGetKernelWorkGroupSize = 295,
|
||||
OpGetKernelPreferredWorkGroupSizeMultiple = 296,
|
||||
OpRetainEvent = 297,
|
||||
OpReleaseEvent = 298,
|
||||
OpCreateUserEvent = 299,
|
||||
OpIsValidEvent = 300,
|
||||
OpSetUserEventStatus = 301,
|
||||
OpCaptureEventProfilingInfo = 302,
|
||||
OpGetDefaultQueue = 303,
|
||||
OpBuildNDRange = 304,
|
||||
OpImageSparseSampleImplicitLod = 305,
|
||||
OpImageSparseSampleExplicitLod = 306,
|
||||
OpImageSparseSampleDrefImplicitLod = 307,
|
||||
OpImageSparseSampleDrefExplicitLod = 308,
|
||||
OpImageSparseSampleProjImplicitLod = 309,
|
||||
OpImageSparseSampleProjExplicitLod = 310,
|
||||
OpImageSparseSampleProjDrefImplicitLod = 311,
|
||||
OpImageSparseSampleProjDrefExplicitLod = 312,
|
||||
OpImageSparseFetch = 313,
|
||||
OpImageSparseGather = 314,
|
||||
OpImageSparseDrefGather = 315,
|
||||
OpImageSparseTexelsResident = 316,
|
||||
OpNoLine = 317,
|
||||
OpAtomicFlagTestAndSet = 318,
|
||||
OpAtomicFlagClear = 319,
|
||||
OpImageSparseRead = 320,
|
||||
OpSizeOf = 321,
|
||||
OpTypePipeStorage = 322,
|
||||
OpConstantPipeStorage = 323,
|
||||
OpCreatePipeFromPipeStorage = 324,
|
||||
OpGetKernelLocalSizeForSubgroupCount = 325,
|
||||
OpGetKernelMaxNumSubgroups = 326,
|
||||
OpTypeNamedBarrier = 327,
|
||||
OpNamedBarrierInitialize = 328,
|
||||
OpMemoryNamedBarrier = 329,
|
||||
OpModuleProcessed = 330,
|
||||
OpExecutionModeId = 331,
|
||||
OpDecorateId = 332,
|
||||
OpGroupNonUniformElect = 333,
|
||||
OpGroupNonUniformAll = 334,
|
||||
OpGroupNonUniformAny = 335,
|
||||
OpGroupNonUniformAllEqual = 336,
|
||||
OpGroupNonUniformBroadcast = 337,
|
||||
OpGroupNonUniformBroadcastFirst = 338,
|
||||
OpGroupNonUniformBallot = 339,
|
||||
OpGroupNonUniformInverseBallot = 340,
|
||||
OpGroupNonUniformBallotBitExtract = 341,
|
||||
OpGroupNonUniformBallotBitCount = 342,
|
||||
OpGroupNonUniformBallotFindLSB = 343,
|
||||
OpGroupNonUniformBallotFindMSB = 344,
|
||||
OpGroupNonUniformShuffle = 345,
|
||||
OpGroupNonUniformShuffleXor = 346,
|
||||
OpGroupNonUniformShuffleUp = 347,
|
||||
OpGroupNonUniformShuffleDown = 348,
|
||||
OpGroupNonUniformIAdd = 349,
|
||||
OpGroupNonUniformFAdd = 350,
|
||||
OpGroupNonUniformIMul = 351,
|
||||
OpGroupNonUniformFMul = 352,
|
||||
OpGroupNonUniformSMin = 353,
|
||||
OpGroupNonUniformUMin = 354,
|
||||
OpGroupNonUniformFMin = 355,
|
||||
OpGroupNonUniformSMax = 356,
|
||||
OpGroupNonUniformUMax = 357,
|
||||
OpGroupNonUniformFMax = 358,
|
||||
OpGroupNonUniformBitwiseAnd = 359,
|
||||
OpGroupNonUniformBitwiseOr = 360,
|
||||
OpGroupNonUniformBitwiseXor = 361,
|
||||
OpGroupNonUniformLogicalAnd = 362,
|
||||
OpGroupNonUniformLogicalOr = 363,
|
||||
OpGroupNonUniformLogicalXor = 364,
|
||||
OpGroupNonUniformQuadBroadcast = 365,
|
||||
OpGroupNonUniformQuadSwap = 366,
|
||||
OpCopyLogical = 400,
|
||||
OpPtrEqual = 401,
|
||||
OpPtrNotEqual = 402,
|
||||
OpPtrDiff = 403,
|
||||
OpSubgroupBallotKHR = 4421,
|
||||
OpSubgroupFirstInvocationKHR = 4422,
|
||||
OpSubgroupAllKHR = 4428,
|
||||
OpSubgroupAnyKHR = 4429,
|
||||
OpSubgroupAllEqualKHR = 4430,
|
||||
OpSubgroupReadInvocationKHR = 4432,
|
||||
OpGroupIAddNonUniformAMD = 5000,
|
||||
OpGroupFAddNonUniformAMD = 5001,
|
||||
OpGroupFMinNonUniformAMD = 5002,
|
||||
OpGroupUMinNonUniformAMD = 5003,
|
||||
OpGroupSMinNonUniformAMD = 5004,
|
||||
OpGroupFMaxNonUniformAMD = 5005,
|
||||
OpGroupUMaxNonUniformAMD = 5006,
|
||||
OpGroupSMaxNonUniformAMD = 5007,
|
||||
OpFragmentMaskFetchAMD = 5011,
|
||||
OpFragmentFetchAMD = 5012,
|
||||
OpImageSampleFootprintNV = 5283,
|
||||
OpGroupNonUniformPartitionNV = 5296,
|
||||
OpWritePackedPrimitiveIndices4x8NV = 5299,
|
||||
OpReportIntersectionNV = 5334,
|
||||
OpIgnoreIntersectionNV = 5335,
|
||||
OpTerminateRayNV = 5336,
|
||||
OpTraceNV = 5337,
|
||||
OpTypeAccelerationStructureNV = 5341,
|
||||
OpExecuteCallableNV = 5344,
|
||||
OpTypeCooperativeMatrixNV = 5358,
|
||||
OpCooperativeMatrixLoadNV = 5359,
|
||||
OpCooperativeMatrixStoreNV = 5360,
|
||||
OpCooperativeMatrixMulAddNV = 5361,
|
||||
OpCooperativeMatrixLengthNV = 5362,
|
||||
OpBeginInvocationInterlockEXT = 5364,
|
||||
OpEndInvocationInterlockEXT = 5365,
|
||||
OpDemoteToHelperInvocationEXT = 5380,
|
||||
OpIsHelperInvocationEXT = 5381,
|
||||
OpSubgroupShuffleINTEL = 5571,
|
||||
OpSubgroupShuffleDownINTEL = 5572,
|
||||
OpSubgroupShuffleUpINTEL = 5573,
|
||||
OpSubgroupShuffleXorINTEL = 5574,
|
||||
OpSubgroupBlockReadINTEL = 5575,
|
||||
OpSubgroupBlockWriteINTEL = 5576,
|
||||
OpSubgroupImageBlockReadINTEL = 5577,
|
||||
OpSubgroupImageBlockWriteINTEL = 5578,
|
||||
OpSubgroupImageMediaBlockReadINTEL = 5580,
|
||||
OpSubgroupImageMediaBlockWriteINTEL = 5581,
|
||||
OpUCountLeadingZerosINTEL = 5585,
|
||||
OpUCountTrailingZerosINTEL = 5586,
|
||||
OpAbsISubINTEL = 5587,
|
||||
OpAbsUSubINTEL = 5588,
|
||||
OpIAddSatINTEL = 5589,
|
||||
OpUAddSatINTEL = 5590,
|
||||
OpIAverageINTEL = 5591,
|
||||
OpUAverageINTEL = 5592,
|
||||
OpIAverageRoundedINTEL = 5593,
|
||||
OpUAverageRoundedINTEL = 5594,
|
||||
OpISubSatINTEL = 5595,
|
||||
OpUSubSatINTEL = 5596,
|
||||
OpIMul32x16INTEL = 5597,
|
||||
OpUMul32x16INTEL = 5598,
|
||||
OpDecorateString = 5632,
|
||||
OpDecorateStringGOOGLE = 5632,
|
||||
OpMemberDecorateString = 5633,
|
||||
OpMemberDecorateStringGOOGLE = 5633,
|
||||
OpVmeImageINTEL = 5699,
|
||||
OpTypeVmeImageINTEL = 5700,
|
||||
OpTypeAvcImePayloadINTEL = 5701,
|
||||
OpTypeAvcRefPayloadINTEL = 5702,
|
||||
OpTypeAvcSicPayloadINTEL = 5703,
|
||||
OpTypeAvcMcePayloadINTEL = 5704,
|
||||
OpTypeAvcMceResultINTEL = 5705,
|
||||
OpTypeAvcImeResultINTEL = 5706,
|
||||
OpTypeAvcImeResultSingleReferenceStreamoutINTEL = 5707,
|
||||
OpTypeAvcImeResultDualReferenceStreamoutINTEL = 5708,
|
||||
OpTypeAvcImeSingleReferenceStreaminINTEL = 5709,
|
||||
OpTypeAvcImeDualReferenceStreaminINTEL = 5710,
|
||||
OpTypeAvcRefResultINTEL = 5711,
|
||||
OpTypeAvcSicResultINTEL = 5712,
|
||||
OpSubgroupAvcMceGetDefaultInterBaseMultiReferencePenaltyINTEL = 5713,
|
||||
OpSubgroupAvcMceSetInterBaseMultiReferencePenaltyINTEL = 5714,
|
||||
OpSubgroupAvcMceGetDefaultInterShapePenaltyINTEL = 5715,
|
||||
OpSubgroupAvcMceSetInterShapePenaltyINTEL = 5716,
|
||||
OpSubgroupAvcMceGetDefaultInterDirectionPenaltyINTEL = 5717,
|
||||
OpSubgroupAvcMceSetInterDirectionPenaltyINTEL = 5718,
|
||||
OpSubgroupAvcMceGetDefaultIntraLumaShapePenaltyINTEL = 5719,
|
||||
OpSubgroupAvcMceGetDefaultInterMotionVectorCostTableINTEL = 5720,
|
||||
OpSubgroupAvcMceGetDefaultHighPenaltyCostTableINTEL = 5721,
|
||||
OpSubgroupAvcMceGetDefaultMediumPenaltyCostTableINTEL = 5722,
|
||||
OpSubgroupAvcMceGetDefaultLowPenaltyCostTableINTEL = 5723,
|
||||
OpSubgroupAvcMceSetMotionVectorCostFunctionINTEL = 5724,
|
||||
OpSubgroupAvcMceGetDefaultIntraLumaModePenaltyINTEL = 5725,
|
||||
OpSubgroupAvcMceGetDefaultNonDcLumaIntraPenaltyINTEL = 5726,
|
||||
OpSubgroupAvcMceGetDefaultIntraChromaModeBasePenaltyINTEL = 5727,
|
||||
OpSubgroupAvcMceSetAcOnlyHaarINTEL = 5728,
|
||||
OpSubgroupAvcMceSetSourceInterlacedFieldPolarityINTEL = 5729,
|
||||
OpSubgroupAvcMceSetSingleReferenceInterlacedFieldPolarityINTEL = 5730,
|
||||
OpSubgroupAvcMceSetDualReferenceInterlacedFieldPolaritiesINTEL = 5731,
|
||||
OpSubgroupAvcMceConvertToImePayloadINTEL = 5732,
|
||||
OpSubgroupAvcMceConvertToImeResultINTEL = 5733,
|
||||
OpSubgroupAvcMceConvertToRefPayloadINTEL = 5734,
|
||||
OpSubgroupAvcMceConvertToRefResultINTEL = 5735,
|
||||
OpSubgroupAvcMceConvertToSicPayloadINTEL = 5736,
|
||||
OpSubgroupAvcMceConvertToSicResultINTEL = 5737,
|
||||
OpSubgroupAvcMceGetMotionVectorsINTEL = 5738,
|
||||
OpSubgroupAvcMceGetInterDistortionsINTEL = 5739,
|
||||
OpSubgroupAvcMceGetBestInterDistortionsINTEL = 5740,
|
||||
OpSubgroupAvcMceGetInterMajorShapeINTEL = 5741,
|
||||
OpSubgroupAvcMceGetInterMinorShapeINTEL = 5742,
|
||||
OpSubgroupAvcMceGetInterDirectionsINTEL = 5743,
|
||||
OpSubgroupAvcMceGetInterMotionVectorCountINTEL = 5744,
|
||||
OpSubgroupAvcMceGetInterReferenceIdsINTEL = 5745,
|
||||
OpSubgroupAvcMceGetInterReferenceInterlacedFieldPolaritiesINTEL = 5746,
|
||||
OpSubgroupAvcImeInitializeINTEL = 5747,
|
||||
OpSubgroupAvcImeSetSingleReferenceINTEL = 5748,
|
||||
OpSubgroupAvcImeSetDualReferenceINTEL = 5749,
|
||||
OpSubgroupAvcImeRefWindowSizeINTEL = 5750,
|
||||
OpSubgroupAvcImeAdjustRefOffsetINTEL = 5751,
|
||||
OpSubgroupAvcImeConvertToMcePayloadINTEL = 5752,
|
||||
OpSubgroupAvcImeSetMaxMotionVectorCountINTEL = 5753,
|
||||
OpSubgroupAvcImeSetUnidirectionalMixDisableINTEL = 5754,
|
||||
OpSubgroupAvcImeSetEarlySearchTerminationThresholdINTEL = 5755,
|
||||
OpSubgroupAvcImeSetWeightedSadINTEL = 5756,
|
||||
OpSubgroupAvcImeEvaluateWithSingleReferenceINTEL = 5757,
|
||||
OpSubgroupAvcImeEvaluateWithDualReferenceINTEL = 5758,
|
||||
OpSubgroupAvcImeEvaluateWithSingleReferenceStreaminINTEL = 5759,
|
||||
OpSubgroupAvcImeEvaluateWithDualReferenceStreaminINTEL = 5760,
|
||||
OpSubgroupAvcImeEvaluateWithSingleReferenceStreamoutINTEL = 5761,
|
||||
OpSubgroupAvcImeEvaluateWithDualReferenceStreamoutINTEL = 5762,
|
||||
OpSubgroupAvcImeEvaluateWithSingleReferenceStreaminoutINTEL = 5763,
|
||||
OpSubgroupAvcImeEvaluateWithDualReferenceStreaminoutINTEL = 5764,
|
||||
OpSubgroupAvcImeConvertToMceResultINTEL = 5765,
|
||||
OpSubgroupAvcImeGetSingleReferenceStreaminINTEL = 5766,
|
||||
OpSubgroupAvcImeGetDualReferenceStreaminINTEL = 5767,
|
||||
OpSubgroupAvcImeStripSingleReferenceStreamoutINTEL = 5768,
|
||||
OpSubgroupAvcImeStripDualReferenceStreamoutINTEL = 5769,
|
||||
OpSubgroupAvcImeGetStreamoutSingleReferenceMajorShapeMotionVectorsINTEL = 5770,
|
||||
OpSubgroupAvcImeGetStreamoutSingleReferenceMajorShapeDistortionsINTEL = 5771,
|
||||
OpSubgroupAvcImeGetStreamoutSingleReferenceMajorShapeReferenceIdsINTEL = 5772,
|
||||
OpSubgroupAvcImeGetStreamoutDualReferenceMajorShapeMotionVectorsINTEL = 5773,
|
||||
OpSubgroupAvcImeGetStreamoutDualReferenceMajorShapeDistortionsINTEL = 5774,
|
||||
OpSubgroupAvcImeGetStreamoutDualReferenceMajorShapeReferenceIdsINTEL = 5775,
|
||||
OpSubgroupAvcImeGetBorderReachedINTEL = 5776,
|
||||
OpSubgroupAvcImeGetTruncatedSearchIndicationINTEL = 5777,
|
||||
OpSubgroupAvcImeGetUnidirectionalEarlySearchTerminationINTEL = 5778,
|
||||
OpSubgroupAvcImeGetWeightingPatternMinimumMotionVectorINTEL = 5779,
|
||||
OpSubgroupAvcImeGetWeightingPatternMinimumDistortionINTEL = 5780,
|
||||
OpSubgroupAvcFmeInitializeINTEL = 5781,
|
||||
OpSubgroupAvcBmeInitializeINTEL = 5782,
|
||||
OpSubgroupAvcRefConvertToMcePayloadINTEL = 5783,
|
||||
OpSubgroupAvcRefSetBidirectionalMixDisableINTEL = 5784,
|
||||
OpSubgroupAvcRefSetBilinearFilterEnableINTEL = 5785,
|
||||
OpSubgroupAvcRefEvaluateWithSingleReferenceINTEL = 5786,
|
||||
OpSubgroupAvcRefEvaluateWithDualReferenceINTEL = 5787,
|
||||
OpSubgroupAvcRefEvaluateWithMultiReferenceINTEL = 5788,
|
||||
OpSubgroupAvcRefEvaluateWithMultiReferenceInterlacedINTEL = 5789,
|
||||
OpSubgroupAvcRefConvertToMceResultINTEL = 5790,
|
||||
OpSubgroupAvcSicInitializeINTEL = 5791,
|
||||
OpSubgroupAvcSicConfigureSkcINTEL = 5792,
|
||||
OpSubgroupAvcSicConfigureIpeLumaINTEL = 5793,
|
||||
OpSubgroupAvcSicConfigureIpeLumaChromaINTEL = 5794,
|
||||
OpSubgroupAvcSicGetMotionVectorMaskINTEL = 5795,
|
||||
OpSubgroupAvcSicConvertToMcePayloadINTEL = 5796,
|
||||
OpSubgroupAvcSicSetIntraLumaShapePenaltyINTEL = 5797,
|
||||
OpSubgroupAvcSicSetIntraLumaModeCostFunctionINTEL = 5798,
|
||||
OpSubgroupAvcSicSetIntraChromaModeCostFunctionINTEL = 5799,
|
||||
OpSubgroupAvcSicSetBilinearFilterEnableINTEL = 5800,
|
||||
OpSubgroupAvcSicSetSkcForwardTransformEnableINTEL = 5801,
|
||||
OpSubgroupAvcSicSetBlockBasedRawSkipSadINTEL = 5802,
|
||||
OpSubgroupAvcSicEvaluateIpeINTEL = 5803,
|
||||
OpSubgroupAvcSicEvaluateWithSingleReferenceINTEL = 5804,
|
||||
OpSubgroupAvcSicEvaluateWithDualReferenceINTEL = 5805,
|
||||
OpSubgroupAvcSicEvaluateWithMultiReferenceINTEL = 5806,
|
||||
OpSubgroupAvcSicEvaluateWithMultiReferenceInterlacedINTEL = 5807,
|
||||
OpSubgroupAvcSicConvertToMceResultINTEL = 5808,
|
||||
OpSubgroupAvcSicGetIpeLumaShapeINTEL = 5809,
|
||||
OpSubgroupAvcSicGetBestIpeLumaDistortionINTEL = 5810,
|
||||
OpSubgroupAvcSicGetBestIpeChromaDistortionINTEL = 5811,
|
||||
OpSubgroupAvcSicGetPackedIpeLumaModesINTEL = 5812,
|
||||
OpSubgroupAvcSicGetIpeChromaModeINTEL = 5813,
|
||||
OpSubgroupAvcSicGetPackedSkcLumaCountThresholdINTEL = 5814,
|
||||
OpSubgroupAvcSicGetPackedSkcLumaSumThresholdINTEL = 5815,
|
||||
OpSubgroupAvcSicGetInterRawSadsINTEL = 5816,
|
||||
OpMax = 0x7fffffff,
|
||||
};
|
||||
|
||||
#ifdef SPV_ENABLE_UTILITY_CODE
|
||||
inline void HasResultAndType(Op opcode, bool *hasResult, bool *hasResultType) {
|
||||
*hasResult = *hasResultType = false;
|
||||
switch (opcode) {
|
||||
default: /* unknown opcode */ break;
|
||||
case OpNop: *hasResult = false; *hasResultType = false; break;
|
||||
case OpUndef: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSourceContinued: *hasResult = false; *hasResultType = false; break;
|
||||
case OpSource: *hasResult = false; *hasResultType = false; break;
|
||||
case OpSourceExtension: *hasResult = false; *hasResultType = false; break;
|
||||
case OpName: *hasResult = false; *hasResultType = false; break;
|
||||
case OpMemberName: *hasResult = false; *hasResultType = false; break;
|
||||
case OpString: *hasResult = true; *hasResultType = false; break;
|
||||
case OpLine: *hasResult = false; *hasResultType = false; break;
|
||||
case OpExtension: *hasResult = false; *hasResultType = false; break;
|
||||
case OpExtInstImport: *hasResult = true; *hasResultType = false; break;
|
||||
case OpExtInst: *hasResult = true; *hasResultType = true; break;
|
||||
case OpMemoryModel: *hasResult = false; *hasResultType = false; break;
|
||||
case OpEntryPoint: *hasResult = false; *hasResultType = false; break;
|
||||
case OpExecutionMode: *hasResult = false; *hasResultType = false; break;
|
||||
case OpCapability: *hasResult = false; *hasResultType = false; break;
|
||||
case OpTypeVoid: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeBool: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeInt: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeFloat: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeVector: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeMatrix: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeImage: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeSampler: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeSampledImage: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeArray: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeRuntimeArray: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeStruct: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeOpaque: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypePointer: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeFunction: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeEvent: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeDeviceEvent: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeReserveId: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeQueue: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypePipe: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeForwardPointer: *hasResult = false; *hasResultType = false; break;
|
||||
case OpConstantTrue: *hasResult = true; *hasResultType = true; break;
|
||||
case OpConstantFalse: *hasResult = true; *hasResultType = true; break;
|
||||
case OpConstant: *hasResult = true; *hasResultType = true; break;
|
||||
case OpConstantComposite: *hasResult = true; *hasResultType = true; break;
|
||||
case OpConstantSampler: *hasResult = true; *hasResultType = true; break;
|
||||
case OpConstantNull: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSpecConstantTrue: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSpecConstantFalse: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSpecConstant: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSpecConstantComposite: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSpecConstantOp: *hasResult = true; *hasResultType = true; break;
|
||||
case OpFunction: *hasResult = true; *hasResultType = true; break;
|
||||
case OpFunctionParameter: *hasResult = true; *hasResultType = true; break;
|
||||
case OpFunctionEnd: *hasResult = false; *hasResultType = false; break;
|
||||
case OpFunctionCall: *hasResult = true; *hasResultType = true; break;
|
||||
case OpVariable: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageTexelPointer: *hasResult = true; *hasResultType = true; break;
|
||||
case OpLoad: *hasResult = true; *hasResultType = true; break;
|
||||
case OpStore: *hasResult = false; *hasResultType = false; break;
|
||||
case OpCopyMemory: *hasResult = false; *hasResultType = false; break;
|
||||
case OpCopyMemorySized: *hasResult = false; *hasResultType = false; break;
|
||||
case OpAccessChain: *hasResult = true; *hasResultType = true; break;
|
||||
case OpInBoundsAccessChain: *hasResult = true; *hasResultType = true; break;
|
||||
case OpPtrAccessChain: *hasResult = true; *hasResultType = true; break;
|
||||
case OpArrayLength: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGenericPtrMemSemantics: *hasResult = true; *hasResultType = true; break;
|
||||
case OpInBoundsPtrAccessChain: *hasResult = true; *hasResultType = true; break;
|
||||
case OpDecorate: *hasResult = false; *hasResultType = false; break;
|
||||
case OpMemberDecorate: *hasResult = false; *hasResultType = false; break;
|
||||
case OpDecorationGroup: *hasResult = true; *hasResultType = false; break;
|
||||
case OpGroupDecorate: *hasResult = false; *hasResultType = false; break;
|
||||
case OpGroupMemberDecorate: *hasResult = false; *hasResultType = false; break;
|
||||
case OpVectorExtractDynamic: *hasResult = true; *hasResultType = true; break;
|
||||
case OpVectorInsertDynamic: *hasResult = true; *hasResultType = true; break;
|
||||
case OpVectorShuffle: *hasResult = true; *hasResultType = true; break;
|
||||
case OpCompositeConstruct: *hasResult = true; *hasResultType = true; break;
|
||||
case OpCompositeExtract: *hasResult = true; *hasResultType = true; break;
|
||||
case OpCompositeInsert: *hasResult = true; *hasResultType = true; break;
|
||||
case OpCopyObject: *hasResult = true; *hasResultType = true; break;
|
||||
case OpTranspose: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSampledImage: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageSampleImplicitLod: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageSampleExplicitLod: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageSampleDrefImplicitLod: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageSampleDrefExplicitLod: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageSampleProjImplicitLod: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageSampleProjExplicitLod: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageSampleProjDrefImplicitLod: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageSampleProjDrefExplicitLod: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageFetch: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageGather: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageDrefGather: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageRead: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageWrite: *hasResult = false; *hasResultType = false; break;
|
||||
case OpImage: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageQueryFormat: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageQueryOrder: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageQuerySizeLod: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageQuerySize: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageQueryLod: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageQueryLevels: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageQuerySamples: *hasResult = true; *hasResultType = true; break;
|
||||
case OpConvertFToU: *hasResult = true; *hasResultType = true; break;
|
||||
case OpConvertFToS: *hasResult = true; *hasResultType = true; break;
|
||||
case OpConvertSToF: *hasResult = true; *hasResultType = true; break;
|
||||
case OpConvertUToF: *hasResult = true; *hasResultType = true; break;
|
||||
case OpUConvert: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSConvert: *hasResult = true; *hasResultType = true; break;
|
||||
case OpFConvert: *hasResult = true; *hasResultType = true; break;
|
||||
case OpQuantizeToF16: *hasResult = true; *hasResultType = true; break;
|
||||
case OpConvertPtrToU: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSatConvertSToU: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSatConvertUToS: *hasResult = true; *hasResultType = true; break;
|
||||
case OpConvertUToPtr: *hasResult = true; *hasResultType = true; break;
|
||||
case OpPtrCastToGeneric: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGenericCastToPtr: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGenericCastToPtrExplicit: *hasResult = true; *hasResultType = true; break;
|
||||
case OpBitcast: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSNegate: *hasResult = true; *hasResultType = true; break;
|
||||
case OpFNegate: *hasResult = true; *hasResultType = true; break;
|
||||
case OpIAdd: *hasResult = true; *hasResultType = true; break;
|
||||
case OpFAdd: *hasResult = true; *hasResultType = true; break;
|
||||
case OpISub: *hasResult = true; *hasResultType = true; break;
|
||||
case OpFSub: *hasResult = true; *hasResultType = true; break;
|
||||
case OpIMul: *hasResult = true; *hasResultType = true; break;
|
||||
case OpFMul: *hasResult = true; *hasResultType = true; break;
|
||||
case OpUDiv: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSDiv: *hasResult = true; *hasResultType = true; break;
|
||||
case OpFDiv: *hasResult = true; *hasResultType = true; break;
|
||||
case OpUMod: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSRem: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSMod: *hasResult = true; *hasResultType = true; break;
|
||||
case OpFRem: *hasResult = true; *hasResultType = true; break;
|
||||
case OpFMod: *hasResult = true; *hasResultType = true; break;
|
||||
case OpVectorTimesScalar: *hasResult = true; *hasResultType = true; break;
|
||||
case OpMatrixTimesScalar: *hasResult = true; *hasResultType = true; break;
|
||||
case OpVectorTimesMatrix: *hasResult = true; *hasResultType = true; break;
|
||||
case OpMatrixTimesVector: *hasResult = true; *hasResultType = true; break;
|
||||
case OpMatrixTimesMatrix: *hasResult = true; *hasResultType = true; break;
|
||||
case OpOuterProduct: *hasResult = true; *hasResultType = true; break;
|
||||
case OpDot: *hasResult = true; *hasResultType = true; break;
|
||||
case OpIAddCarry: *hasResult = true; *hasResultType = true; break;
|
||||
case OpISubBorrow: *hasResult = true; *hasResultType = true; break;
|
||||
case OpUMulExtended: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSMulExtended: *hasResult = true; *hasResultType = true; break;
|
||||
case OpAny: *hasResult = true; *hasResultType = true; break;
|
||||
case OpAll: *hasResult = true; *hasResultType = true; break;
|
||||
case OpIsNan: *hasResult = true; *hasResultType = true; break;
|
||||
case OpIsInf: *hasResult = true; *hasResultType = true; break;
|
||||
case OpIsFinite: *hasResult = true; *hasResultType = true; break;
|
||||
case OpIsNormal: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSignBitSet: *hasResult = true; *hasResultType = true; break;
|
||||
case OpLessOrGreater: *hasResult = true; *hasResultType = true; break;
|
||||
case OpOrdered: *hasResult = true; *hasResultType = true; break;
|
||||
case OpUnordered: *hasResult = true; *hasResultType = true; break;
|
||||
case OpLogicalEqual: *hasResult = true; *hasResultType = true; break;
|
||||
case OpLogicalNotEqual: *hasResult = true; *hasResultType = true; break;
|
||||
case OpLogicalOr: *hasResult = true; *hasResultType = true; break;
|
||||
case OpLogicalAnd: *hasResult = true; *hasResultType = true; break;
|
||||
case OpLogicalNot: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSelect: *hasResult = true; *hasResultType = true; break;
|
||||
case OpIEqual: *hasResult = true; *hasResultType = true; break;
|
||||
case OpINotEqual: *hasResult = true; *hasResultType = true; break;
|
||||
case OpUGreaterThan: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSGreaterThan: *hasResult = true; *hasResultType = true; break;
|
||||
case OpUGreaterThanEqual: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSGreaterThanEqual: *hasResult = true; *hasResultType = true; break;
|
||||
case OpULessThan: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSLessThan: *hasResult = true; *hasResultType = true; break;
|
||||
case OpULessThanEqual: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSLessThanEqual: *hasResult = true; *hasResultType = true; break;
|
||||
case OpFOrdEqual: *hasResult = true; *hasResultType = true; break;
|
||||
case OpFUnordEqual: *hasResult = true; *hasResultType = true; break;
|
||||
case OpFOrdNotEqual: *hasResult = true; *hasResultType = true; break;
|
||||
case OpFUnordNotEqual: *hasResult = true; *hasResultType = true; break;
|
||||
case OpFOrdLessThan: *hasResult = true; *hasResultType = true; break;
|
||||
case OpFUnordLessThan: *hasResult = true; *hasResultType = true; break;
|
||||
case OpFOrdGreaterThan: *hasResult = true; *hasResultType = true; break;
|
||||
case OpFUnordGreaterThan: *hasResult = true; *hasResultType = true; break;
|
||||
case OpFOrdLessThanEqual: *hasResult = true; *hasResultType = true; break;
|
||||
case OpFUnordLessThanEqual: *hasResult = true; *hasResultType = true; break;
|
||||
case OpFOrdGreaterThanEqual: *hasResult = true; *hasResultType = true; break;
|
||||
case OpFUnordGreaterThanEqual: *hasResult = true; *hasResultType = true; break;
|
||||
case OpShiftRightLogical: *hasResult = true; *hasResultType = true; break;
|
||||
case OpShiftRightArithmetic: *hasResult = true; *hasResultType = true; break;
|
||||
case OpShiftLeftLogical: *hasResult = true; *hasResultType = true; break;
|
||||
case OpBitwiseOr: *hasResult = true; *hasResultType = true; break;
|
||||
case OpBitwiseXor: *hasResult = true; *hasResultType = true; break;
|
||||
case OpBitwiseAnd: *hasResult = true; *hasResultType = true; break;
|
||||
case OpNot: *hasResult = true; *hasResultType = true; break;
|
||||
case OpBitFieldInsert: *hasResult = true; *hasResultType = true; break;
|
||||
case OpBitFieldSExtract: *hasResult = true; *hasResultType = true; break;
|
||||
case OpBitFieldUExtract: *hasResult = true; *hasResultType = true; break;
|
||||
case OpBitReverse: *hasResult = true; *hasResultType = true; break;
|
||||
case OpBitCount: *hasResult = true; *hasResultType = true; break;
|
||||
case OpDPdx: *hasResult = true; *hasResultType = true; break;
|
||||
case OpDPdy: *hasResult = true; *hasResultType = true; break;
|
||||
case OpFwidth: *hasResult = true; *hasResultType = true; break;
|
||||
case OpDPdxFine: *hasResult = true; *hasResultType = true; break;
|
||||
case OpDPdyFine: *hasResult = true; *hasResultType = true; break;
|
||||
case OpFwidthFine: *hasResult = true; *hasResultType = true; break;
|
||||
case OpDPdxCoarse: *hasResult = true; *hasResultType = true; break;
|
||||
case OpDPdyCoarse: *hasResult = true; *hasResultType = true; break;
|
||||
case OpFwidthCoarse: *hasResult = true; *hasResultType = true; break;
|
||||
case OpEmitVertex: *hasResult = false; *hasResultType = false; break;
|
||||
case OpEndPrimitive: *hasResult = false; *hasResultType = false; break;
|
||||
case OpEmitStreamVertex: *hasResult = false; *hasResultType = false; break;
|
||||
case OpEndStreamPrimitive: *hasResult = false; *hasResultType = false; break;
|
||||
case OpControlBarrier: *hasResult = false; *hasResultType = false; break;
|
||||
case OpMemoryBarrier: *hasResult = false; *hasResultType = false; break;
|
||||
case OpAtomicLoad: *hasResult = true; *hasResultType = true; break;
|
||||
case OpAtomicStore: *hasResult = false; *hasResultType = false; break;
|
||||
case OpAtomicExchange: *hasResult = true; *hasResultType = true; break;
|
||||
case OpAtomicCompareExchange: *hasResult = true; *hasResultType = true; break;
|
||||
case OpAtomicCompareExchangeWeak: *hasResult = true; *hasResultType = true; break;
|
||||
case OpAtomicIIncrement: *hasResult = true; *hasResultType = true; break;
|
||||
case OpAtomicIDecrement: *hasResult = true; *hasResultType = true; break;
|
||||
case OpAtomicIAdd: *hasResult = true; *hasResultType = true; break;
|
||||
case OpAtomicISub: *hasResult = true; *hasResultType = true; break;
|
||||
case OpAtomicSMin: *hasResult = true; *hasResultType = true; break;
|
||||
case OpAtomicUMin: *hasResult = true; *hasResultType = true; break;
|
||||
case OpAtomicSMax: *hasResult = true; *hasResultType = true; break;
|
||||
case OpAtomicUMax: *hasResult = true; *hasResultType = true; break;
|
||||
case OpAtomicAnd: *hasResult = true; *hasResultType = true; break;
|
||||
case OpAtomicOr: *hasResult = true; *hasResultType = true; break;
|
||||
case OpAtomicXor: *hasResult = true; *hasResultType = true; break;
|
||||
case OpPhi: *hasResult = true; *hasResultType = true; break;
|
||||
case OpLoopMerge: *hasResult = false; *hasResultType = false; break;
|
||||
case OpSelectionMerge: *hasResult = false; *hasResultType = false; break;
|
||||
case OpLabel: *hasResult = true; *hasResultType = false; break;
|
||||
case OpBranch: *hasResult = false; *hasResultType = false; break;
|
||||
case OpBranchConditional: *hasResult = false; *hasResultType = false; break;
|
||||
case OpSwitch: *hasResult = false; *hasResultType = false; break;
|
||||
case OpKill: *hasResult = false; *hasResultType = false; break;
|
||||
case OpReturn: *hasResult = false; *hasResultType = false; break;
|
||||
case OpReturnValue: *hasResult = false; *hasResultType = false; break;
|
||||
case OpUnreachable: *hasResult = false; *hasResultType = false; break;
|
||||
case OpLifetimeStart: *hasResult = false; *hasResultType = false; break;
|
||||
case OpLifetimeStop: *hasResult = false; *hasResultType = false; break;
|
||||
case OpGroupAsyncCopy: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupWaitEvents: *hasResult = false; *hasResultType = false; break;
|
||||
case OpGroupAll: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupAny: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupBroadcast: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupIAdd: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupFAdd: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupFMin: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupUMin: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupSMin: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupFMax: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupUMax: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupSMax: *hasResult = true; *hasResultType = true; break;
|
||||
case OpReadPipe: *hasResult = true; *hasResultType = true; break;
|
||||
case OpWritePipe: *hasResult = true; *hasResultType = true; break;
|
||||
case OpReservedReadPipe: *hasResult = true; *hasResultType = true; break;
|
||||
case OpReservedWritePipe: *hasResult = true; *hasResultType = true; break;
|
||||
case OpReserveReadPipePackets: *hasResult = true; *hasResultType = true; break;
|
||||
case OpReserveWritePipePackets: *hasResult = true; *hasResultType = true; break;
|
||||
case OpCommitReadPipe: *hasResult = false; *hasResultType = false; break;
|
||||
case OpCommitWritePipe: *hasResult = false; *hasResultType = false; break;
|
||||
case OpIsValidReserveId: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGetNumPipePackets: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGetMaxPipePackets: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupReserveReadPipePackets: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupReserveWritePipePackets: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupCommitReadPipe: *hasResult = false; *hasResultType = false; break;
|
||||
case OpGroupCommitWritePipe: *hasResult = false; *hasResultType = false; break;
|
||||
case OpEnqueueMarker: *hasResult = true; *hasResultType = true; break;
|
||||
case OpEnqueueKernel: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGetKernelNDrangeSubGroupCount: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGetKernelNDrangeMaxSubGroupSize: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGetKernelWorkGroupSize: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGetKernelPreferredWorkGroupSizeMultiple: *hasResult = true; *hasResultType = true; break;
|
||||
case OpRetainEvent: *hasResult = false; *hasResultType = false; break;
|
||||
case OpReleaseEvent: *hasResult = false; *hasResultType = false; break;
|
||||
case OpCreateUserEvent: *hasResult = true; *hasResultType = true; break;
|
||||
case OpIsValidEvent: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSetUserEventStatus: *hasResult = false; *hasResultType = false; break;
|
||||
case OpCaptureEventProfilingInfo: *hasResult = false; *hasResultType = false; break;
|
||||
case OpGetDefaultQueue: *hasResult = true; *hasResultType = true; break;
|
||||
case OpBuildNDRange: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageSparseSampleImplicitLod: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageSparseSampleExplicitLod: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageSparseSampleDrefImplicitLod: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageSparseSampleDrefExplicitLod: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageSparseSampleProjImplicitLod: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageSparseSampleProjExplicitLod: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageSparseSampleProjDrefImplicitLod: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageSparseSampleProjDrefExplicitLod: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageSparseFetch: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageSparseGather: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageSparseDrefGather: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageSparseTexelsResident: *hasResult = true; *hasResultType = true; break;
|
||||
case OpNoLine: *hasResult = false; *hasResultType = false; break;
|
||||
case OpAtomicFlagTestAndSet: *hasResult = true; *hasResultType = true; break;
|
||||
case OpAtomicFlagClear: *hasResult = false; *hasResultType = false; break;
|
||||
case OpImageSparseRead: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSizeOf: *hasResult = true; *hasResultType = true; break;
|
||||
case OpTypePipeStorage: *hasResult = true; *hasResultType = false; break;
|
||||
case OpConstantPipeStorage: *hasResult = true; *hasResultType = true; break;
|
||||
case OpCreatePipeFromPipeStorage: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGetKernelLocalSizeForSubgroupCount: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGetKernelMaxNumSubgroups: *hasResult = true; *hasResultType = true; break;
|
||||
case OpTypeNamedBarrier: *hasResult = true; *hasResultType = false; break;
|
||||
case OpNamedBarrierInitialize: *hasResult = true; *hasResultType = true; break;
|
||||
case OpMemoryNamedBarrier: *hasResult = false; *hasResultType = false; break;
|
||||
case OpModuleProcessed: *hasResult = false; *hasResultType = false; break;
|
||||
case OpExecutionModeId: *hasResult = false; *hasResultType = false; break;
|
||||
case OpDecorateId: *hasResult = false; *hasResultType = false; break;
|
||||
case OpGroupNonUniformElect: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformAll: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformAny: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformAllEqual: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformBroadcast: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformBroadcastFirst: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformBallot: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformInverseBallot: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformBallotBitExtract: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformBallotBitCount: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformBallotFindLSB: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformBallotFindMSB: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformShuffle: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformShuffleXor: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformShuffleUp: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformShuffleDown: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformIAdd: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformFAdd: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformIMul: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformFMul: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformSMin: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformUMin: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformFMin: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformSMax: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformUMax: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformFMax: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformBitwiseAnd: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformBitwiseOr: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformBitwiseXor: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformLogicalAnd: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformLogicalOr: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformLogicalXor: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformQuadBroadcast: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformQuadSwap: *hasResult = true; *hasResultType = true; break;
|
||||
case OpCopyLogical: *hasResult = true; *hasResultType = true; break;
|
||||
case OpPtrEqual: *hasResult = true; *hasResultType = true; break;
|
||||
case OpPtrNotEqual: *hasResult = true; *hasResultType = true; break;
|
||||
case OpPtrDiff: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupBallotKHR: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupFirstInvocationKHR: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAllKHR: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAnyKHR: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAllEqualKHR: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupReadInvocationKHR: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupIAddNonUniformAMD: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupFAddNonUniformAMD: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupFMinNonUniformAMD: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupUMinNonUniformAMD: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupSMinNonUniformAMD: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupFMaxNonUniformAMD: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupUMaxNonUniformAMD: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupSMaxNonUniformAMD: *hasResult = true; *hasResultType = true; break;
|
||||
case OpFragmentMaskFetchAMD: *hasResult = true; *hasResultType = true; break;
|
||||
case OpFragmentFetchAMD: *hasResult = true; *hasResultType = true; break;
|
||||
case OpImageSampleFootprintNV: *hasResult = true; *hasResultType = true; break;
|
||||
case OpGroupNonUniformPartitionNV: *hasResult = true; *hasResultType = true; break;
|
||||
case OpWritePackedPrimitiveIndices4x8NV: *hasResult = false; *hasResultType = false; break;
|
||||
case OpReportIntersectionNV: *hasResult = true; *hasResultType = true; break;
|
||||
case OpIgnoreIntersectionNV: *hasResult = false; *hasResultType = false; break;
|
||||
case OpTerminateRayNV: *hasResult = false; *hasResultType = false; break;
|
||||
case OpTraceNV: *hasResult = false; *hasResultType = false; break;
|
||||
case OpTypeAccelerationStructureNV: *hasResult = true; *hasResultType = false; break;
|
||||
case OpExecuteCallableNV: *hasResult = false; *hasResultType = false; break;
|
||||
case OpTypeCooperativeMatrixNV: *hasResult = true; *hasResultType = false; break;
|
||||
case OpCooperativeMatrixLoadNV: *hasResult = true; *hasResultType = true; break;
|
||||
case OpCooperativeMatrixStoreNV: *hasResult = false; *hasResultType = false; break;
|
||||
case OpCooperativeMatrixMulAddNV: *hasResult = true; *hasResultType = true; break;
|
||||
case OpCooperativeMatrixLengthNV: *hasResult = true; *hasResultType = true; break;
|
||||
case OpBeginInvocationInterlockEXT: *hasResult = false; *hasResultType = false; break;
|
||||
case OpEndInvocationInterlockEXT: *hasResult = false; *hasResultType = false; break;
|
||||
case OpDemoteToHelperInvocationEXT: *hasResult = false; *hasResultType = false; break;
|
||||
case OpIsHelperInvocationEXT: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupShuffleINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupShuffleDownINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupShuffleUpINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupShuffleXorINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupBlockReadINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupBlockWriteINTEL: *hasResult = false; *hasResultType = false; break;
|
||||
case OpSubgroupImageBlockReadINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupImageBlockWriteINTEL: *hasResult = false; *hasResultType = false; break;
|
||||
case OpSubgroupImageMediaBlockReadINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupImageMediaBlockWriteINTEL: *hasResult = false; *hasResultType = false; break;
|
||||
case OpUCountLeadingZerosINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpUCountTrailingZerosINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpAbsISubINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpAbsUSubINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpIAddSatINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpUAddSatINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpIAverageINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpUAverageINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpIAverageRoundedINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpUAverageRoundedINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpISubSatINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpUSubSatINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpIMul32x16INTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpUMul32x16INTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpDecorateString: *hasResult = false; *hasResultType = false; break;
|
||||
case OpMemberDecorateString: *hasResult = false; *hasResultType = false; break;
|
||||
case OpVmeImageINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpTypeVmeImageINTEL: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeAvcImePayloadINTEL: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeAvcRefPayloadINTEL: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeAvcSicPayloadINTEL: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeAvcMcePayloadINTEL: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeAvcMceResultINTEL: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeAvcImeResultINTEL: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeAvcImeResultSingleReferenceStreamoutINTEL: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeAvcImeResultDualReferenceStreamoutINTEL: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeAvcImeSingleReferenceStreaminINTEL: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeAvcImeDualReferenceStreaminINTEL: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeAvcRefResultINTEL: *hasResult = true; *hasResultType = false; break;
|
||||
case OpTypeAvcSicResultINTEL: *hasResult = true; *hasResultType = false; break;
|
||||
case OpSubgroupAvcMceGetDefaultInterBaseMultiReferencePenaltyINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceSetInterBaseMultiReferencePenaltyINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceGetDefaultInterShapePenaltyINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceSetInterShapePenaltyINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceGetDefaultInterDirectionPenaltyINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceSetInterDirectionPenaltyINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceGetDefaultIntraLumaShapePenaltyINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceGetDefaultInterMotionVectorCostTableINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceGetDefaultHighPenaltyCostTableINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceGetDefaultMediumPenaltyCostTableINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceGetDefaultLowPenaltyCostTableINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceSetMotionVectorCostFunctionINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceGetDefaultIntraLumaModePenaltyINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceGetDefaultNonDcLumaIntraPenaltyINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceGetDefaultIntraChromaModeBasePenaltyINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceSetAcOnlyHaarINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceSetSourceInterlacedFieldPolarityINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceSetSingleReferenceInterlacedFieldPolarityINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceSetDualReferenceInterlacedFieldPolaritiesINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceConvertToImePayloadINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceConvertToImeResultINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceConvertToRefPayloadINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceConvertToRefResultINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceConvertToSicPayloadINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceConvertToSicResultINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceGetMotionVectorsINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceGetInterDistortionsINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceGetBestInterDistortionsINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceGetInterMajorShapeINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceGetInterMinorShapeINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceGetInterDirectionsINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceGetInterMotionVectorCountINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceGetInterReferenceIdsINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcMceGetInterReferenceInterlacedFieldPolaritiesINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeInitializeINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeSetSingleReferenceINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeSetDualReferenceINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeRefWindowSizeINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeAdjustRefOffsetINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeConvertToMcePayloadINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeSetMaxMotionVectorCountINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeSetUnidirectionalMixDisableINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeSetEarlySearchTerminationThresholdINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeSetWeightedSadINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeEvaluateWithSingleReferenceINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeEvaluateWithDualReferenceINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeEvaluateWithSingleReferenceStreaminINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeEvaluateWithDualReferenceStreaminINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeEvaluateWithSingleReferenceStreamoutINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeEvaluateWithDualReferenceStreamoutINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeEvaluateWithSingleReferenceStreaminoutINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeEvaluateWithDualReferenceStreaminoutINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeConvertToMceResultINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeGetSingleReferenceStreaminINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeGetDualReferenceStreaminINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeStripSingleReferenceStreamoutINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeStripDualReferenceStreamoutINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeGetStreamoutSingleReferenceMajorShapeMotionVectorsINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeGetStreamoutSingleReferenceMajorShapeDistortionsINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeGetStreamoutSingleReferenceMajorShapeReferenceIdsINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeGetStreamoutDualReferenceMajorShapeMotionVectorsINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeGetStreamoutDualReferenceMajorShapeDistortionsINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeGetStreamoutDualReferenceMajorShapeReferenceIdsINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeGetBorderReachedINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeGetTruncatedSearchIndicationINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeGetUnidirectionalEarlySearchTerminationINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeGetWeightingPatternMinimumMotionVectorINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcImeGetWeightingPatternMinimumDistortionINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcFmeInitializeINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcBmeInitializeINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcRefConvertToMcePayloadINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcRefSetBidirectionalMixDisableINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcRefSetBilinearFilterEnableINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcRefEvaluateWithSingleReferenceINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcRefEvaluateWithDualReferenceINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcRefEvaluateWithMultiReferenceINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcRefEvaluateWithMultiReferenceInterlacedINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcRefConvertToMceResultINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcSicInitializeINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcSicConfigureSkcINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcSicConfigureIpeLumaINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcSicConfigureIpeLumaChromaINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcSicGetMotionVectorMaskINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcSicConvertToMcePayloadINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcSicSetIntraLumaShapePenaltyINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcSicSetIntraLumaModeCostFunctionINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcSicSetIntraChromaModeCostFunctionINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcSicSetBilinearFilterEnableINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcSicSetSkcForwardTransformEnableINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcSicSetBlockBasedRawSkipSadINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcSicEvaluateIpeINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcSicEvaluateWithSingleReferenceINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcSicEvaluateWithDualReferenceINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcSicEvaluateWithMultiReferenceINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcSicEvaluateWithMultiReferenceInterlacedINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcSicConvertToMceResultINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcSicGetIpeLumaShapeINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcSicGetBestIpeLumaDistortionINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcSicGetBestIpeChromaDistortionINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcSicGetPackedIpeLumaModesINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcSicGetIpeChromaModeINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcSicGetPackedSkcLumaCountThresholdINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcSicGetPackedSkcLumaSumThresholdINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
case OpSubgroupAvcSicGetInterRawSadsINTEL: *hasResult = true; *hasResultType = true; break;
|
||||
}
|
||||
}
|
||||
#endif /* SPV_ENABLE_UTILITY_CODE */
|
||||
|
||||
// Overload operator| for mask bit combining
|
||||
|
||||
inline ImageOperandsMask operator|(ImageOperandsMask a, ImageOperandsMask b) { return ImageOperandsMask(unsigned(a) | unsigned(b)); }
|
||||
inline FPFastMathModeMask operator|(FPFastMathModeMask a, FPFastMathModeMask b) { return FPFastMathModeMask(unsigned(a) | unsigned(b)); }
|
||||
inline SelectionControlMask operator|(SelectionControlMask a, SelectionControlMask b) { return SelectionControlMask(unsigned(a) | unsigned(b)); }
|
||||
inline LoopControlMask operator|(LoopControlMask a, LoopControlMask b) { return LoopControlMask(unsigned(a) | unsigned(b)); }
|
||||
inline FunctionControlMask operator|(FunctionControlMask a, FunctionControlMask b) { return FunctionControlMask(unsigned(a) | unsigned(b)); }
|
||||
inline MemorySemanticsMask operator|(MemorySemanticsMask a, MemorySemanticsMask b) { return MemorySemanticsMask(unsigned(a) | unsigned(b)); }
|
||||
inline MemoryAccessMask operator|(MemoryAccessMask a, MemoryAccessMask b) { return MemoryAccessMask(unsigned(a) | unsigned(b)); }
|
||||
inline KernelProfilingInfoMask operator|(KernelProfilingInfoMask a, KernelProfilingInfoMask b) { return KernelProfilingInfoMask(unsigned(a) | unsigned(b)); }
|
||||
|
||||
} // end namespace spv
|
||||
|
||||
#endif // #ifndef spirv_HPP
|
||||
|
1
include/vulkan
Submodule
1
include/vulkan
Submodule
@ -0,0 +1 @@
|
||||
Subproject commit 85c2334e92e215cce34e8e0ed8b2dce4700f4a50
|
@ -1,84 +0,0 @@
|
||||
//
|
||||
// File: vk_platform.h
|
||||
//
|
||||
/*
|
||||
** Copyright 2014-2021 The Khronos Group Inc.
|
||||
**
|
||||
** SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
|
||||
#ifndef VK_PLATFORM_H_
|
||||
#define VK_PLATFORM_H_
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C"
|
||||
{
|
||||
#endif // __cplusplus
|
||||
|
||||
/*
|
||||
***************************************************************************************************
|
||||
* Platform-specific directives and type declarations
|
||||
***************************************************************************************************
|
||||
*/
|
||||
|
||||
/* Platform-specific calling convention macros.
|
||||
*
|
||||
* Platforms should define these so that Vulkan clients call Vulkan commands
|
||||
* with the same calling conventions that the Vulkan implementation expects.
|
||||
*
|
||||
* VKAPI_ATTR - Placed before the return type in function declarations.
|
||||
* Useful for C++11 and GCC/Clang-style function attribute syntax.
|
||||
* VKAPI_CALL - Placed after the return type in function declarations.
|
||||
* Useful for MSVC-style calling convention syntax.
|
||||
* VKAPI_PTR - Placed between the '(' and '*' in function pointer types.
|
||||
*
|
||||
* Function declaration: VKAPI_ATTR void VKAPI_CALL vkCommand(void);
|
||||
* Function pointer type: typedef void (VKAPI_PTR *PFN_vkCommand)(void);
|
||||
*/
|
||||
#if defined(_WIN32)
|
||||
// On Windows, Vulkan commands use the stdcall convention
|
||||
#define VKAPI_ATTR
|
||||
#define VKAPI_CALL __stdcall
|
||||
#define VKAPI_PTR VKAPI_CALL
|
||||
#elif defined(__ANDROID__) && defined(__ARM_ARCH) && __ARM_ARCH < 7
|
||||
#error "Vulkan isn't supported for the 'armeabi' NDK ABI"
|
||||
#elif defined(__ANDROID__) && defined(__ARM_ARCH) && __ARM_ARCH >= 7 && defined(__ARM_32BIT_STATE)
|
||||
// On Android 32-bit ARM targets, Vulkan functions use the "hardfloat"
|
||||
// calling convention, i.e. float parameters are passed in registers. This
|
||||
// is true even if the rest of the application passes floats on the stack,
|
||||
// as it does by default when compiling for the armeabi-v7a NDK ABI.
|
||||
#define VKAPI_ATTR __attribute__((pcs("aapcs-vfp")))
|
||||
#define VKAPI_CALL
|
||||
#define VKAPI_PTR VKAPI_ATTR
|
||||
#else
|
||||
// On other platforms, use the default calling convention
|
||||
#define VKAPI_ATTR
|
||||
#define VKAPI_CALL
|
||||
#define VKAPI_PTR
|
||||
#endif
|
||||
|
||||
#if !defined(VK_NO_STDDEF_H)
|
||||
#include <stddef.h>
|
||||
#endif // !defined(VK_NO_STDDEF_H)
|
||||
|
||||
#if !defined(VK_NO_STDINT_H)
|
||||
#if defined(_MSC_VER) && (_MSC_VER < 1600)
|
||||
typedef signed __int8 int8_t;
|
||||
typedef unsigned __int8 uint8_t;
|
||||
typedef signed __int16 int16_t;
|
||||
typedef unsigned __int16 uint16_t;
|
||||
typedef signed __int32 int32_t;
|
||||
typedef unsigned __int32 uint32_t;
|
||||
typedef signed __int64 int64_t;
|
||||
typedef unsigned __int64 uint64_t;
|
||||
#else
|
||||
#include <stdint.h>
|
||||
#endif
|
||||
#endif // !defined(VK_NO_STDINT_H)
|
||||
|
||||
#ifdef __cplusplus
|
||||
} // extern "C"
|
||||
#endif // __cplusplus
|
||||
|
||||
#endif
|
@ -1,92 +0,0 @@
|
||||
#ifndef VULKAN_H_
|
||||
#define VULKAN_H_ 1
|
||||
|
||||
/*
|
||||
** Copyright 2015-2021 The Khronos Group Inc.
|
||||
**
|
||||
** SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
#include "vk_platform.h"
|
||||
#include "vulkan_core.h"
|
||||
|
||||
#ifdef VK_USE_PLATFORM_ANDROID_KHR
|
||||
#include "vulkan_android.h"
|
||||
#endif
|
||||
|
||||
#ifdef VK_USE_PLATFORM_FUCHSIA
|
||||
#include <zircon/types.h>
|
||||
#include "vulkan_fuchsia.h"
|
||||
#endif
|
||||
|
||||
#ifdef VK_USE_PLATFORM_IOS_MVK
|
||||
#include "vulkan_ios.h"
|
||||
#endif
|
||||
|
||||
|
||||
#ifdef VK_USE_PLATFORM_MACOS_MVK
|
||||
#include "vulkan_macos.h"
|
||||
#endif
|
||||
|
||||
#ifdef VK_USE_PLATFORM_METAL_EXT
|
||||
#include "vulkan_metal.h"
|
||||
#endif
|
||||
|
||||
#ifdef VK_USE_PLATFORM_VI_NN
|
||||
#include "vulkan_vi.h"
|
||||
#endif
|
||||
|
||||
|
||||
#ifdef VK_USE_PLATFORM_WAYLAND_KHR
|
||||
#include <wayland-client.h>
|
||||
#include "vulkan_wayland.h"
|
||||
#endif
|
||||
|
||||
|
||||
#ifdef VK_USE_PLATFORM_WIN32_KHR
|
||||
#include <windows.h>
|
||||
#include "vulkan_win32.h"
|
||||
#endif
|
||||
|
||||
|
||||
#ifdef VK_USE_PLATFORM_XCB_KHR
|
||||
#include <xcb/xcb.h>
|
||||
#include "vulkan_xcb.h"
|
||||
#endif
|
||||
|
||||
|
||||
#ifdef VK_USE_PLATFORM_XLIB_KHR
|
||||
#include <X11/Xlib.h>
|
||||
#include "vulkan_xlib.h"
|
||||
#endif
|
||||
|
||||
|
||||
#ifdef VK_USE_PLATFORM_DIRECTFB_EXT
|
||||
#include <directfb.h>
|
||||
#include "vulkan_directfb.h"
|
||||
#endif
|
||||
|
||||
|
||||
#ifdef VK_USE_PLATFORM_XLIB_XRANDR_EXT
|
||||
#include <X11/Xlib.h>
|
||||
#include <X11/extensions/Xrandr.h>
|
||||
#include "vulkan_xlib_xrandr.h"
|
||||
#endif
|
||||
|
||||
|
||||
#ifdef VK_USE_PLATFORM_GGP
|
||||
#include <ggp_c/vulkan_types.h>
|
||||
#include "vulkan_ggp.h"
|
||||
#endif
|
||||
|
||||
|
||||
#ifdef VK_USE_PLATFORM_SCREEN_QNX
|
||||
#include <screen/screen.h>
|
||||
#include "vulkan_screen.h"
|
||||
#endif
|
||||
|
||||
#ifdef VK_ENABLE_BETA_EXTENSIONS
|
||||
#include "vulkan_beta.h"
|
||||
#endif
|
||||
|
||||
#endif // VULKAN_H_
|
File diff suppressed because it is too large
Load Diff
@ -1,315 +0,0 @@
|
||||
#ifndef VULKAN_WIN32_H_
|
||||
#define VULKAN_WIN32_H_ 1
|
||||
|
||||
/*
|
||||
** Copyright 2015-2021 The Khronos Group Inc.
|
||||
**
|
||||
** SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
/*
|
||||
** This header is generated from the Khronos Vulkan XML API Registry.
|
||||
**
|
||||
*/
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
#define VK_KHR_win32_surface 1
|
||||
#define VK_KHR_WIN32_SURFACE_SPEC_VERSION 6
|
||||
#define VK_KHR_WIN32_SURFACE_EXTENSION_NAME "VK_KHR_win32_surface"
|
||||
typedef VkFlags VkWin32SurfaceCreateFlagsKHR;
|
||||
typedef struct VkWin32SurfaceCreateInfoKHR {
|
||||
VkStructureType sType;
|
||||
const void* pNext;
|
||||
VkWin32SurfaceCreateFlagsKHR flags;
|
||||
HINSTANCE hinstance;
|
||||
HWND hwnd;
|
||||
} VkWin32SurfaceCreateInfoKHR;
|
||||
|
||||
typedef VkResult (VKAPI_PTR *PFN_vkCreateWin32SurfaceKHR)(VkInstance instance, const VkWin32SurfaceCreateInfoKHR* pCreateInfo, const VkAllocationCallbacks* pAllocator, VkSurfaceKHR* pSurface);
|
||||
typedef VkBool32 (VKAPI_PTR *PFN_vkGetPhysicalDeviceWin32PresentationSupportKHR)(VkPhysicalDevice physicalDevice, uint32_t queueFamilyIndex);
|
||||
|
||||
#ifndef VK_NO_PROTOTYPES
|
||||
VKAPI_ATTR VkResult VKAPI_CALL vkCreateWin32SurfaceKHR(
|
||||
VkInstance instance,
|
||||
const VkWin32SurfaceCreateInfoKHR* pCreateInfo,
|
||||
const VkAllocationCallbacks* pAllocator,
|
||||
VkSurfaceKHR* pSurface);
|
||||
|
||||
VKAPI_ATTR VkBool32 VKAPI_CALL vkGetPhysicalDeviceWin32PresentationSupportKHR(
|
||||
VkPhysicalDevice physicalDevice,
|
||||
uint32_t queueFamilyIndex);
|
||||
#endif
|
||||
|
||||
|
||||
#define VK_KHR_external_memory_win32 1
|
||||
#define VK_KHR_EXTERNAL_MEMORY_WIN32_SPEC_VERSION 1
|
||||
#define VK_KHR_EXTERNAL_MEMORY_WIN32_EXTENSION_NAME "VK_KHR_external_memory_win32"
|
||||
typedef struct VkImportMemoryWin32HandleInfoKHR {
|
||||
VkStructureType sType;
|
||||
const void* pNext;
|
||||
VkExternalMemoryHandleTypeFlagBits handleType;
|
||||
HANDLE handle;
|
||||
LPCWSTR name;
|
||||
} VkImportMemoryWin32HandleInfoKHR;
|
||||
|
||||
typedef struct VkExportMemoryWin32HandleInfoKHR {
|
||||
VkStructureType sType;
|
||||
const void* pNext;
|
||||
const SECURITY_ATTRIBUTES* pAttributes;
|
||||
DWORD dwAccess;
|
||||
LPCWSTR name;
|
||||
} VkExportMemoryWin32HandleInfoKHR;
|
||||
|
||||
typedef struct VkMemoryWin32HandlePropertiesKHR {
|
||||
VkStructureType sType;
|
||||
void* pNext;
|
||||
uint32_t memoryTypeBits;
|
||||
} VkMemoryWin32HandlePropertiesKHR;
|
||||
|
||||
typedef struct VkMemoryGetWin32HandleInfoKHR {
|
||||
VkStructureType sType;
|
||||
const void* pNext;
|
||||
VkDeviceMemory memory;
|
||||
VkExternalMemoryHandleTypeFlagBits handleType;
|
||||
} VkMemoryGetWin32HandleInfoKHR;
|
||||
|
||||
typedef VkResult (VKAPI_PTR *PFN_vkGetMemoryWin32HandleKHR)(VkDevice device, const VkMemoryGetWin32HandleInfoKHR* pGetWin32HandleInfo, HANDLE* pHandle);
|
||||
typedef VkResult (VKAPI_PTR *PFN_vkGetMemoryWin32HandlePropertiesKHR)(VkDevice device, VkExternalMemoryHandleTypeFlagBits handleType, HANDLE handle, VkMemoryWin32HandlePropertiesKHR* pMemoryWin32HandleProperties);
|
||||
|
||||
#ifndef VK_NO_PROTOTYPES
|
||||
VKAPI_ATTR VkResult VKAPI_CALL vkGetMemoryWin32HandleKHR(
|
||||
VkDevice device,
|
||||
const VkMemoryGetWin32HandleInfoKHR* pGetWin32HandleInfo,
|
||||
HANDLE* pHandle);
|
||||
|
||||
VKAPI_ATTR VkResult VKAPI_CALL vkGetMemoryWin32HandlePropertiesKHR(
|
||||
VkDevice device,
|
||||
VkExternalMemoryHandleTypeFlagBits handleType,
|
||||
HANDLE handle,
|
||||
VkMemoryWin32HandlePropertiesKHR* pMemoryWin32HandleProperties);
|
||||
#endif
|
||||
|
||||
|
||||
#define VK_KHR_win32_keyed_mutex 1
|
||||
#define VK_KHR_WIN32_KEYED_MUTEX_SPEC_VERSION 1
|
||||
#define VK_KHR_WIN32_KEYED_MUTEX_EXTENSION_NAME "VK_KHR_win32_keyed_mutex"
|
||||
typedef struct VkWin32KeyedMutexAcquireReleaseInfoKHR {
|
||||
VkStructureType sType;
|
||||
const void* pNext;
|
||||
uint32_t acquireCount;
|
||||
const VkDeviceMemory* pAcquireSyncs;
|
||||
const uint64_t* pAcquireKeys;
|
||||
const uint32_t* pAcquireTimeouts;
|
||||
uint32_t releaseCount;
|
||||
const VkDeviceMemory* pReleaseSyncs;
|
||||
const uint64_t* pReleaseKeys;
|
||||
} VkWin32KeyedMutexAcquireReleaseInfoKHR;
|
||||
|
||||
|
||||
|
||||
#define VK_KHR_external_semaphore_win32 1
|
||||
#define VK_KHR_EXTERNAL_SEMAPHORE_WIN32_SPEC_VERSION 1
|
||||
#define VK_KHR_EXTERNAL_SEMAPHORE_WIN32_EXTENSION_NAME "VK_KHR_external_semaphore_win32"
|
||||
typedef struct VkImportSemaphoreWin32HandleInfoKHR {
|
||||
VkStructureType sType;
|
||||
const void* pNext;
|
||||
VkSemaphore semaphore;
|
||||
VkSemaphoreImportFlags flags;
|
||||
VkExternalSemaphoreHandleTypeFlagBits handleType;
|
||||
HANDLE handle;
|
||||
LPCWSTR name;
|
||||
} VkImportSemaphoreWin32HandleInfoKHR;
|
||||
|
||||
typedef struct VkExportSemaphoreWin32HandleInfoKHR {
|
||||
VkStructureType sType;
|
||||
const void* pNext;
|
||||
const SECURITY_ATTRIBUTES* pAttributes;
|
||||
DWORD dwAccess;
|
||||
LPCWSTR name;
|
||||
} VkExportSemaphoreWin32HandleInfoKHR;
|
||||
|
||||
typedef struct VkD3D12FenceSubmitInfoKHR {
|
||||
VkStructureType sType;
|
||||
const void* pNext;
|
||||
uint32_t waitSemaphoreValuesCount;
|
||||
const uint64_t* pWaitSemaphoreValues;
|
||||
uint32_t signalSemaphoreValuesCount;
|
||||
const uint64_t* pSignalSemaphoreValues;
|
||||
} VkD3D12FenceSubmitInfoKHR;
|
||||
|
||||
typedef struct VkSemaphoreGetWin32HandleInfoKHR {
|
||||
VkStructureType sType;
|
||||
const void* pNext;
|
||||
VkSemaphore semaphore;
|
||||
VkExternalSemaphoreHandleTypeFlagBits handleType;
|
||||
} VkSemaphoreGetWin32HandleInfoKHR;
|
||||
|
||||
typedef VkResult (VKAPI_PTR *PFN_vkImportSemaphoreWin32HandleKHR)(VkDevice device, const VkImportSemaphoreWin32HandleInfoKHR* pImportSemaphoreWin32HandleInfo);
|
||||
typedef VkResult (VKAPI_PTR *PFN_vkGetSemaphoreWin32HandleKHR)(VkDevice device, const VkSemaphoreGetWin32HandleInfoKHR* pGetWin32HandleInfo, HANDLE* pHandle);
|
||||
|
||||
#ifndef VK_NO_PROTOTYPES
|
||||
VKAPI_ATTR VkResult VKAPI_CALL vkImportSemaphoreWin32HandleKHR(
|
||||
VkDevice device,
|
||||
const VkImportSemaphoreWin32HandleInfoKHR* pImportSemaphoreWin32HandleInfo);
|
||||
|
||||
VKAPI_ATTR VkResult VKAPI_CALL vkGetSemaphoreWin32HandleKHR(
|
||||
VkDevice device,
|
||||
const VkSemaphoreGetWin32HandleInfoKHR* pGetWin32HandleInfo,
|
||||
HANDLE* pHandle);
|
||||
#endif
|
||||
|
||||
|
||||
#define VK_KHR_external_fence_win32 1
|
||||
#define VK_KHR_EXTERNAL_FENCE_WIN32_SPEC_VERSION 1
|
||||
#define VK_KHR_EXTERNAL_FENCE_WIN32_EXTENSION_NAME "VK_KHR_external_fence_win32"
|
||||
typedef struct VkImportFenceWin32HandleInfoKHR {
|
||||
VkStructureType sType;
|
||||
const void* pNext;
|
||||
VkFence fence;
|
||||
VkFenceImportFlags flags;
|
||||
VkExternalFenceHandleTypeFlagBits handleType;
|
||||
HANDLE handle;
|
||||
LPCWSTR name;
|
||||
} VkImportFenceWin32HandleInfoKHR;
|
||||
|
||||
typedef struct VkExportFenceWin32HandleInfoKHR {
|
||||
VkStructureType sType;
|
||||
const void* pNext;
|
||||
const SECURITY_ATTRIBUTES* pAttributes;
|
||||
DWORD dwAccess;
|
||||
LPCWSTR name;
|
||||
} VkExportFenceWin32HandleInfoKHR;
|
||||
|
||||
typedef struct VkFenceGetWin32HandleInfoKHR {
|
||||
VkStructureType sType;
|
||||
const void* pNext;
|
||||
VkFence fence;
|
||||
VkExternalFenceHandleTypeFlagBits handleType;
|
||||
} VkFenceGetWin32HandleInfoKHR;
|
||||
|
||||
typedef VkResult (VKAPI_PTR *PFN_vkImportFenceWin32HandleKHR)(VkDevice device, const VkImportFenceWin32HandleInfoKHR* pImportFenceWin32HandleInfo);
|
||||
typedef VkResult (VKAPI_PTR *PFN_vkGetFenceWin32HandleKHR)(VkDevice device, const VkFenceGetWin32HandleInfoKHR* pGetWin32HandleInfo, HANDLE* pHandle);
|
||||
|
||||
#ifndef VK_NO_PROTOTYPES
|
||||
VKAPI_ATTR VkResult VKAPI_CALL vkImportFenceWin32HandleKHR(
|
||||
VkDevice device,
|
||||
const VkImportFenceWin32HandleInfoKHR* pImportFenceWin32HandleInfo);
|
||||
|
||||
VKAPI_ATTR VkResult VKAPI_CALL vkGetFenceWin32HandleKHR(
|
||||
VkDevice device,
|
||||
const VkFenceGetWin32HandleInfoKHR* pGetWin32HandleInfo,
|
||||
HANDLE* pHandle);
|
||||
#endif
|
||||
|
||||
|
||||
#define VK_NV_external_memory_win32 1
|
||||
#define VK_NV_EXTERNAL_MEMORY_WIN32_SPEC_VERSION 1
|
||||
#define VK_NV_EXTERNAL_MEMORY_WIN32_EXTENSION_NAME "VK_NV_external_memory_win32"
|
||||
typedef struct VkImportMemoryWin32HandleInfoNV {
|
||||
VkStructureType sType;
|
||||
const void* pNext;
|
||||
VkExternalMemoryHandleTypeFlagsNV handleType;
|
||||
HANDLE handle;
|
||||
} VkImportMemoryWin32HandleInfoNV;
|
||||
|
||||
typedef struct VkExportMemoryWin32HandleInfoNV {
|
||||
VkStructureType sType;
|
||||
const void* pNext;
|
||||
const SECURITY_ATTRIBUTES* pAttributes;
|
||||
DWORD dwAccess;
|
||||
} VkExportMemoryWin32HandleInfoNV;
|
||||
|
||||
typedef VkResult (VKAPI_PTR *PFN_vkGetMemoryWin32HandleNV)(VkDevice device, VkDeviceMemory memory, VkExternalMemoryHandleTypeFlagsNV handleType, HANDLE* pHandle);
|
||||
|
||||
#ifndef VK_NO_PROTOTYPES
|
||||
VKAPI_ATTR VkResult VKAPI_CALL vkGetMemoryWin32HandleNV(
|
||||
VkDevice device,
|
||||
VkDeviceMemory memory,
|
||||
VkExternalMemoryHandleTypeFlagsNV handleType,
|
||||
HANDLE* pHandle);
|
||||
#endif
|
||||
|
||||
|
||||
#define VK_NV_win32_keyed_mutex 1
|
||||
#define VK_NV_WIN32_KEYED_MUTEX_SPEC_VERSION 2
|
||||
#define VK_NV_WIN32_KEYED_MUTEX_EXTENSION_NAME "VK_NV_win32_keyed_mutex"
|
||||
typedef struct VkWin32KeyedMutexAcquireReleaseInfoNV {
|
||||
VkStructureType sType;
|
||||
const void* pNext;
|
||||
uint32_t acquireCount;
|
||||
const VkDeviceMemory* pAcquireSyncs;
|
||||
const uint64_t* pAcquireKeys;
|
||||
const uint32_t* pAcquireTimeoutMilliseconds;
|
||||
uint32_t releaseCount;
|
||||
const VkDeviceMemory* pReleaseSyncs;
|
||||
const uint64_t* pReleaseKeys;
|
||||
} VkWin32KeyedMutexAcquireReleaseInfoNV;
|
||||
|
||||
|
||||
|
||||
#define VK_EXT_full_screen_exclusive 1
|
||||
#define VK_EXT_FULL_SCREEN_EXCLUSIVE_SPEC_VERSION 4
|
||||
#define VK_EXT_FULL_SCREEN_EXCLUSIVE_EXTENSION_NAME "VK_EXT_full_screen_exclusive"
|
||||
|
||||
typedef enum VkFullScreenExclusiveEXT {
|
||||
VK_FULL_SCREEN_EXCLUSIVE_DEFAULT_EXT = 0,
|
||||
VK_FULL_SCREEN_EXCLUSIVE_ALLOWED_EXT = 1,
|
||||
VK_FULL_SCREEN_EXCLUSIVE_DISALLOWED_EXT = 2,
|
||||
VK_FULL_SCREEN_EXCLUSIVE_APPLICATION_CONTROLLED_EXT = 3,
|
||||
VK_FULL_SCREEN_EXCLUSIVE_MAX_ENUM_EXT = 0x7FFFFFFF
|
||||
} VkFullScreenExclusiveEXT;
|
||||
typedef struct VkSurfaceFullScreenExclusiveInfoEXT {
|
||||
VkStructureType sType;
|
||||
void* pNext;
|
||||
VkFullScreenExclusiveEXT fullScreenExclusive;
|
||||
} VkSurfaceFullScreenExclusiveInfoEXT;
|
||||
|
||||
typedef struct VkSurfaceCapabilitiesFullScreenExclusiveEXT {
|
||||
VkStructureType sType;
|
||||
void* pNext;
|
||||
VkBool32 fullScreenExclusiveSupported;
|
||||
} VkSurfaceCapabilitiesFullScreenExclusiveEXT;
|
||||
|
||||
typedef struct VkSurfaceFullScreenExclusiveWin32InfoEXT {
|
||||
VkStructureType sType;
|
||||
const void* pNext;
|
||||
HMONITOR hmonitor;
|
||||
} VkSurfaceFullScreenExclusiveWin32InfoEXT;
|
||||
|
||||
typedef VkResult (VKAPI_PTR *PFN_vkGetPhysicalDeviceSurfacePresentModes2EXT)(VkPhysicalDevice physicalDevice, const VkPhysicalDeviceSurfaceInfo2KHR* pSurfaceInfo, uint32_t* pPresentModeCount, VkPresentModeKHR* pPresentModes);
|
||||
typedef VkResult (VKAPI_PTR *PFN_vkAcquireFullScreenExclusiveModeEXT)(VkDevice device, VkSwapchainKHR swapchain);
|
||||
typedef VkResult (VKAPI_PTR *PFN_vkReleaseFullScreenExclusiveModeEXT)(VkDevice device, VkSwapchainKHR swapchain);
|
||||
typedef VkResult (VKAPI_PTR *PFN_vkGetDeviceGroupSurfacePresentModes2EXT)(VkDevice device, const VkPhysicalDeviceSurfaceInfo2KHR* pSurfaceInfo, VkDeviceGroupPresentModeFlagsKHR* pModes);
|
||||
|
||||
#ifndef VK_NO_PROTOTYPES
|
||||
VKAPI_ATTR VkResult VKAPI_CALL vkGetPhysicalDeviceSurfacePresentModes2EXT(
|
||||
VkPhysicalDevice physicalDevice,
|
||||
const VkPhysicalDeviceSurfaceInfo2KHR* pSurfaceInfo,
|
||||
uint32_t* pPresentModeCount,
|
||||
VkPresentModeKHR* pPresentModes);
|
||||
|
||||
VKAPI_ATTR VkResult VKAPI_CALL vkAcquireFullScreenExclusiveModeEXT(
|
||||
VkDevice device,
|
||||
VkSwapchainKHR swapchain);
|
||||
|
||||
VKAPI_ATTR VkResult VKAPI_CALL vkReleaseFullScreenExclusiveModeEXT(
|
||||
VkDevice device,
|
||||
VkSwapchainKHR swapchain);
|
||||
|
||||
VKAPI_ATTR VkResult VKAPI_CALL vkGetDeviceGroupSurfacePresentModes2EXT(
|
||||
VkDevice device,
|
||||
const VkPhysicalDeviceSurfaceInfo2KHR* pSurfaceInfo,
|
||||
VkDeviceGroupPresentModeFlagsKHR* pModes);
|
||||
#endif
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif
|
Binary file not shown.
@ -1,17 +0,0 @@
|
||||
; File generated automatically from d3dcompiler_43.spec; do not edit!
|
||||
|
||||
LIBRARY d3dcompiler_43.dll
|
||||
|
||||
EXPORTS
|
||||
D3DAssemble @1
|
||||
D3DCompile @3
|
||||
D3DCreateBlob @5
|
||||
D3DDisassemble @8
|
||||
D3DGetBlobPart @9
|
||||
D3DGetDebugInfo @10
|
||||
D3DGetInputAndOutputSignatureBlob @11
|
||||
D3DGetInputSignatureBlob @12
|
||||
D3DGetOutputSignatureBlob @13
|
||||
D3DPreprocess @14
|
||||
D3DReflect @15
|
||||
D3DStripShader @17
|
BIN
lib/vulkan-1.lib
BIN
lib/vulkan-1.lib
Binary file not shown.
Binary file not shown.
@ -1,17 +0,0 @@
|
||||
; File generated automatically from d3dcompiler_43.spec; do not edit!
|
||||
|
||||
LIBRARY d3dcompiler_43.dll
|
||||
|
||||
EXPORTS
|
||||
D3DAssemble@32 @1
|
||||
D3DCompile@44 @3
|
||||
D3DCreateBlob@8 @5
|
||||
D3DDisassemble@20 @8
|
||||
D3DGetBlobPart@20 @9
|
||||
D3DGetDebugInfo@12 @10
|
||||
D3DGetInputAndOutputSignatureBlob@12 @11
|
||||
D3DGetInputSignatureBlob@12 @12
|
||||
D3DGetOutputSignatureBlob@12 @13
|
||||
D3DPreprocess@28 @14
|
||||
D3DReflect@16 @15
|
||||
D3DStripShader@16 @17
|
Binary file not shown.
189
meson.build
189
meson.build
@ -1,40 +1,31 @@
|
||||
project('dxvk', ['c', 'cpp'], version : 'v1.10.1', meson_version : '>= 0.49', default_options : [ 'cpp_std=c++17' ])
|
||||
project('dxvk', ['c', 'cpp'], version : 'v2.2', meson_version : '>= 0.49', default_options : [ 'cpp_std=c++17', 'warning_level=2' ])
|
||||
|
||||
cpu_family = target_machine.cpu_family()
|
||||
platform = target_machine.system()
|
||||
|
||||
cpp = meson.get_compiler('cpp')
|
||||
cc = meson.get_compiler('c')
|
||||
dxvk_is_msvc = cpp.get_id() == 'msvc'
|
||||
|
||||
compiler_args = [
|
||||
'-DNOMINMAX',
|
||||
'-D_WIN32_WINNT=0xa00',
|
||||
'-msse',
|
||||
'-msse2',
|
||||
'-msse3',
|
||||
'-mfpmath=sse',
|
||||
'-Wimplicit-fallthrough',
|
||||
# gcc
|
||||
'-Wno-missing-field-initializers',
|
||||
'-Wno-unused-parameter',
|
||||
'-Wno-cast-function-type', # Needed for GetProcAddress.
|
||||
# clang
|
||||
'-Wno-unused-private-field',
|
||||
'-Wno-microsoft-exception-spec',
|
||||
'-Wno-extern-c-compat',
|
||||
'-Wno-unused-const-variable',
|
||||
'-Wno-missing-braces',
|
||||
]
|
||||
|
||||
link_args = [
|
||||
'-static',
|
||||
'-static-libgcc',
|
||||
'-static-libstdc++',
|
||||
# We need to set the section alignment for debug symbols to
|
||||
# work properly as well as avoiding a memcpy from the Wine loader.
|
||||
'-Wl,--file-alignment=4096',
|
||||
]
|
||||
|
||||
# Wine's built-in back traces only work with dwarf2 symbols
|
||||
if get_option('debug') and target_machine.system() == 'windows'
|
||||
compiler_args += [
|
||||
'-gstrict-dwarf',
|
||||
'-gdwarf-2',
|
||||
]
|
||||
endif
|
||||
link_args = []
|
||||
|
||||
if get_option('build_id')
|
||||
link_args += [
|
||||
@ -42,71 +33,129 @@ if get_option('build_id')
|
||||
]
|
||||
endif
|
||||
|
||||
if cpu_family == 'x86'
|
||||
dxvk_include_dirs = [
|
||||
'./include',
|
||||
'./include/vulkan/include',
|
||||
'./include/spirv/include'
|
||||
]
|
||||
|
||||
proj_displayinfo = subproject('libdisplay-info')
|
||||
dep_displayinfo = proj_displayinfo.get_variable('di_dep')
|
||||
|
||||
if platform == 'windows'
|
||||
compiler_args += [
|
||||
'-DNOMINMAX',
|
||||
'-D_WIN32_WINNT=0xa00',
|
||||
]
|
||||
|
||||
link_args += [
|
||||
'-Wl,--enable-stdcall-fixup',
|
||||
'-Wl,--add-stdcall-alias',
|
||||
'-static',
|
||||
'-static-libgcc',
|
||||
'-static-libstdc++',
|
||||
# We need to set the section alignment for debug symbols to
|
||||
# work properly as well as avoiding a memcpy from the Wine loader.
|
||||
'-Wl,--file-alignment=4096',
|
||||
]
|
||||
|
||||
# Wine's built-in back traces only work with dwarf4 symbols
|
||||
if get_option('debug')
|
||||
compiler_args += [
|
||||
'-gdwarf-4',
|
||||
]
|
||||
endif
|
||||
|
||||
# Enable stdcall fixup on 32-bit
|
||||
if cpu_family == 'x86'
|
||||
link_args += [
|
||||
'-Wl,--enable-stdcall-fixup',
|
||||
'-Wl,--kill-at',
|
||||
]
|
||||
endif
|
||||
|
||||
lib_d3d9 = cpp.find_library('d3d9')
|
||||
lib_d3d11 = cpp.find_library('d3d11')
|
||||
lib_dxgi = cpp.find_library('dxgi')
|
||||
|
||||
if dxvk_is_msvc
|
||||
lib_d3dcompiler_47 = cpp.find_library('d3dcompiler')
|
||||
else
|
||||
lib_d3dcompiler_47 = cpp.find_library('d3dcompiler_47')
|
||||
endif
|
||||
|
||||
if dxvk_is_msvc
|
||||
res_ext = '.res'
|
||||
wrc = find_program('rc')
|
||||
wrc_generator = generator(wrc,
|
||||
output : [ '@BASENAME@' + res_ext ],
|
||||
arguments : [ '/fo', '@OUTPUT@', '@INPUT@' ],
|
||||
)
|
||||
else
|
||||
res_ext = '.o'
|
||||
wrc = find_program('windres')
|
||||
wrc_generator = generator(wrc,
|
||||
output : [ '@BASENAME@' + res_ext ],
|
||||
arguments : [ '-i', '@INPUT@', '-o', '@OUTPUT@' ],
|
||||
)
|
||||
endif
|
||||
|
||||
dxvk_wsi = 'win32'
|
||||
dxvk_name_prefix = ''
|
||||
compiler_args += ['-DDXVK_WSI_WIN32']
|
||||
else
|
||||
wrc = find_program('touch')
|
||||
wrc_generator = generator(wrc, output : [ '@BASENAME@_ignored.h' ], arguments : [ '@OUTPUT@' ] )
|
||||
|
||||
dxvk_include_dirs += [
|
||||
'./include/native',
|
||||
'./include/native/windows',
|
||||
'./include/native/directx'
|
||||
]
|
||||
|
||||
dxvk_wsi = get_option('dxvk_native_wsi')
|
||||
|
||||
if dxvk_wsi == 'sdl2'
|
||||
lib_sdl2 = cpp.find_library('SDL2')
|
||||
compiler_args += ['-DDXVK_WSI_SDL2']
|
||||
elif dxvk_wsi == 'glfw'
|
||||
lib_glfw = cpp.find_library('glfw')
|
||||
compiler_args += ['-DDXVK_WSI_GLFW']
|
||||
endif
|
||||
|
||||
dxvk_name_prefix = 'libdxvk_'
|
||||
|
||||
link_args += [
|
||||
'-static-libgcc',
|
||||
'-static-libstdc++',
|
||||
]
|
||||
endif
|
||||
|
||||
dxvk_include_path = include_directories(dxvk_include_dirs)
|
||||
|
||||
add_project_arguments(cpp.get_supported_arguments(compiler_args), language: 'cpp')
|
||||
add_project_arguments(cc.get_supported_arguments(compiler_args), language: 'c')
|
||||
add_project_link_arguments(cpp.get_supported_link_arguments(link_args), language: 'cpp')
|
||||
add_project_link_arguments(cc.get_supported_link_arguments(link_args), language: 'c')
|
||||
|
||||
dxvk_include_path = include_directories('./include')
|
||||
|
||||
if (cpu_family == 'x86_64')
|
||||
dxvk_library_path = meson.source_root() + '/lib'
|
||||
else
|
||||
dxvk_library_path = meson.source_root() + '/lib32'
|
||||
endif
|
||||
|
||||
dxvk_extradep = [ ]
|
||||
|
||||
lib_vulkan = cpp.find_library('vulkan-1', dirs : dxvk_library_path)
|
||||
lib_d3d9 = cpp.find_library('d3d9')
|
||||
lib_d3d11 = cpp.find_library('d3d11')
|
||||
lib_dxgi = cpp.find_library('dxgi')
|
||||
lib_d3dcompiler_43 = cpp.find_library('d3dcompiler_43', dirs : dxvk_library_path)
|
||||
|
||||
if dxvk_is_msvc
|
||||
lib_d3dcompiler_47 = cpp.find_library('d3dcompiler')
|
||||
else
|
||||
lib_d3dcompiler_47 = cpp.find_library('d3dcompiler_47')
|
||||
endif
|
||||
|
||||
exe_ext = ''
|
||||
dll_ext = ''
|
||||
|
||||
def_spec_ext = '.def'
|
||||
|
||||
glsl_compiler = find_program('glslangValidator')
|
||||
glsl_args = [ '-V', '--vn', '@BASENAME@', '@INPUT@', '-o', '@OUTPUT@' ]
|
||||
if run_command(glsl_compiler, [ '--quiet', '--version' ], check : false).returncode() == 0
|
||||
glsl_args += [ '--quiet' ]
|
||||
endif
|
||||
glsl_generator = generator(glsl_compiler,
|
||||
glsl_compiler = find_program('glslang', 'glslangValidator')
|
||||
glsl_args = [
|
||||
'--quiet',
|
||||
'--target-env', 'vulkan1.2',
|
||||
'--vn', '@BASENAME@',
|
||||
'--depfile', '@DEPFILE@',
|
||||
'@INPUT@',
|
||||
'-o', '@OUTPUT@',
|
||||
]
|
||||
glsl_generator = generator(
|
||||
glsl_compiler,
|
||||
output : [ '@BASENAME@.h' ],
|
||||
depfile : '@BASENAME@.h.d',
|
||||
arguments : glsl_args,
|
||||
)
|
||||
|
||||
if dxvk_is_msvc
|
||||
res_ext = '.res'
|
||||
wrc = find_program('rc')
|
||||
wrc_generator = generator(wrc,
|
||||
output : [ '@BASENAME@' + res_ext ],
|
||||
arguments : [ '/fo', '@OUTPUT@', '@INPUT@' ],
|
||||
)
|
||||
else
|
||||
res_ext = '.o'
|
||||
wrc = find_program('windres')
|
||||
wrc_generator = generator(wrc,
|
||||
output : [ '@BASENAME@' + res_ext ],
|
||||
arguments : [ '-i', '@INPUT@', '-o', '@OUTPUT@' ],
|
||||
)
|
||||
endif
|
||||
|
||||
dxvk_version = vcs_tag(
|
||||
command: ['git', 'describe', '--dirty=+'],
|
||||
input: 'version.h.in',
|
||||
@ -114,9 +163,3 @@ dxvk_version = vcs_tag(
|
||||
)
|
||||
|
||||
subdir('src')
|
||||
|
||||
enable_tests = get_option('enable_tests')
|
||||
|
||||
if enable_tests
|
||||
subdir('tests')
|
||||
endif
|
||||
|
@ -1,6 +1,7 @@
|
||||
option('enable_tests', type : 'boolean', value : false)
|
||||
option('enable_dxgi', type : 'boolean', value : true, description: 'Build DXGI')
|
||||
option('enable_d3d9', type : 'boolean', value : true, description: 'Build D3D9')
|
||||
option('enable_d3d10', type : 'boolean', value : true, description: 'Build D3D10')
|
||||
option('enable_d3d11', type : 'boolean', value : true, description: 'Build D3D11')
|
||||
option('build_id', type : 'boolean', value : false)
|
||||
|
||||
option('dxvk_native_wsi', type : 'string', value : 'sdl2', description: 'WSI system to use if building natively.')
|
88
package-native.sh
Executable file
88
package-native.sh
Executable file
@ -0,0 +1,88 @@
|
||||
#!/usr/bin/env bash
|
||||
|
||||
set -e
|
||||
|
||||
shopt -s extglob
|
||||
|
||||
if [ -z "$1" ] || [ -z "$2" ]; then
|
||||
echo "Usage: $0 version destdir [--no-package] [--dev-build]"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
DXVK_VERSION="$1"
|
||||
DXVK_SRC_DIR=$(readlink -f "$0")
|
||||
DXVK_SRC_DIR=$(dirname "$DXVK_SRC_DIR")
|
||||
DXVK_BUILD_DIR=$(realpath "$2")"/dxvk-native-$DXVK_VERSION"
|
||||
DXVK_ARCHIVE_PATH=$(realpath "$2")"/dxvk-native-$DXVK_VERSION.tar.gz"
|
||||
|
||||
if [ -e "$DXVK_BUILD_DIR" ]; then
|
||||
echo "Build directory $DXVK_BUILD_DIR already exists"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
shift 2
|
||||
|
||||
opt_nopackage=0
|
||||
opt_devbuild=0
|
||||
opt_buildid=false
|
||||
|
||||
CC=${CC:="gcc"}
|
||||
CXX=${CXX:="g++"}
|
||||
|
||||
while [ $# -gt 0 ]; do
|
||||
case "$1" in
|
||||
"--no-package")
|
||||
opt_nopackage=1
|
||||
;;
|
||||
"--dev-build")
|
||||
opt_nopackage=1
|
||||
opt_devbuild=1
|
||||
;;
|
||||
"--build-id")
|
||||
opt_buildid=true
|
||||
;;
|
||||
*)
|
||||
echo "Unrecognized option: $1" >&2
|
||||
exit 1
|
||||
esac
|
||||
shift
|
||||
done
|
||||
|
||||
function build_arch {
|
||||
cd "$DXVK_SRC_DIR"
|
||||
|
||||
opt_strip=
|
||||
if [ $opt_devbuild -eq 0 ]; then
|
||||
opt_strip=--strip
|
||||
fi
|
||||
|
||||
CC="$CC -m$1" CXX="$CXX -m$1" meson setup \
|
||||
--buildtype "release" \
|
||||
--prefix "$DXVK_BUILD_DIR/usr" \
|
||||
$opt_strip \
|
||||
--bindir "$2" \
|
||||
--libdir "$2" \
|
||||
-Dbuild_id=$opt_buildid \
|
||||
"$DXVK_BUILD_DIR/build.$1"
|
||||
|
||||
cd "$DXVK_BUILD_DIR/build.$1"
|
||||
ninja install
|
||||
|
||||
if [ $opt_devbuild -eq 0 ]; then
|
||||
rm -r "$DXVK_BUILD_DIR/build.$1"
|
||||
fi
|
||||
}
|
||||
|
||||
function package {
|
||||
cd "$DXVK_BUILD_DIR"
|
||||
tar -czf "$DXVK_ARCHIVE_PATH" "usr"
|
||||
cd ".."
|
||||
rm -R "dxvk-native-$DXVK_VERSION"
|
||||
}
|
||||
|
||||
build_arch 64 lib
|
||||
build_arch 32 lib32
|
||||
|
||||
if [ $opt_nopackage -eq 0 ]; then
|
||||
package
|
||||
fi
|
@ -10,7 +10,8 @@ if [ -z "$1" ] || [ -z "$2" ]; then
|
||||
fi
|
||||
|
||||
DXVK_VERSION="$1"
|
||||
DXVK_SRC_DIR=`dirname $(readlink -f $0)`
|
||||
DXVK_SRC_DIR=$(readlink -f "$0")
|
||||
DXVK_SRC_DIR=$(dirname "$DXVK_SRC_DIR")
|
||||
DXVK_BUILD_DIR=$(realpath "$2")"/dxvk-$DXVK_VERSION"
|
||||
DXVK_ARCHIVE_PATH=$(realpath "$2")"/dxvk-$DXVK_VERSION.tar.gz"
|
||||
|
||||
@ -57,14 +58,13 @@ function build_arch {
|
||||
opt_strip=--strip
|
||||
fi
|
||||
|
||||
meson --cross-file "$DXVK_SRC_DIR/$crossfile$1.txt" \
|
||||
--buildtype "release" \
|
||||
--prefix "$DXVK_BUILD_DIR" \
|
||||
$opt_strip \
|
||||
--bindir "x$1" \
|
||||
--libdir "x$1" \
|
||||
-Denable_tests=false \
|
||||
-Dbuild_id=$opt_buildid \
|
||||
meson setup --cross-file "$DXVK_SRC_DIR/$crossfile$1.txt" \
|
||||
--buildtype "release" \
|
||||
--prefix "$DXVK_BUILD_DIR" \
|
||||
$opt_strip \
|
||||
--bindir "x$1" \
|
||||
--libdir "x$1" \
|
||||
-Dbuild_id=$opt_buildid \
|
||||
"$DXVK_BUILD_DIR/build.$1"
|
||||
|
||||
cd "$DXVK_BUILD_DIR/build.$1"
|
||||
@ -77,11 +77,6 @@ function build_arch {
|
||||
fi
|
||||
}
|
||||
|
||||
function build_script {
|
||||
cp "$DXVK_SRC_DIR/setup_dxvk.sh" "$DXVK_BUILD_DIR/setup_dxvk.sh"
|
||||
chmod +x "$DXVK_BUILD_DIR/setup_dxvk.sh"
|
||||
}
|
||||
|
||||
function package {
|
||||
cd "$DXVK_BUILD_DIR/.."
|
||||
tar -czf "$DXVK_ARCHIVE_PATH" "dxvk-$DXVK_VERSION"
|
||||
@ -90,7 +85,6 @@ function package {
|
||||
|
||||
build_arch 64
|
||||
build_arch 32
|
||||
build_script
|
||||
|
||||
if [ $opt_nopackage -eq 0 ]; then
|
||||
package
|
||||
|
216
setup_dxvk.sh
216
setup_dxvk.sh
@ -1,216 +0,0 @@
|
||||
#!/usr/bin/env bash
|
||||
|
||||
# default directories
|
||||
dxvk_lib32=${dxvk_lib32:-"x32"}
|
||||
dxvk_lib64=${dxvk_lib64:-"x64"}
|
||||
|
||||
# figure out where we are
|
||||
basedir=$(dirname "$(readlink -f $0)")
|
||||
|
||||
# figure out which action to perform
|
||||
action="$1"
|
||||
|
||||
case "$action" in
|
||||
install)
|
||||
;;
|
||||
uninstall)
|
||||
;;
|
||||
*)
|
||||
echo "Unrecognized action: $action"
|
||||
echo "Usage: $0 [install|uninstall] [--without-dxgi] [--with-d3d10] [--symlink]"
|
||||
exit 1
|
||||
esac
|
||||
|
||||
# process arguments
|
||||
shift
|
||||
|
||||
with_dxgi=true
|
||||
with_d3d10=false
|
||||
file_cmd="cp -v"
|
||||
|
||||
while (($# > 0)); do
|
||||
case "$1" in
|
||||
"--without-dxgi")
|
||||
with_dxgi=false
|
||||
;;
|
||||
"--with-d3d10")
|
||||
with_d3d10=true
|
||||
;;
|
||||
"--symlink")
|
||||
file_cmd="ln -s -v"
|
||||
;;
|
||||
esac
|
||||
shift
|
||||
done
|
||||
|
||||
# check wine prefix before invoking wine, so that we
|
||||
# don't accidentally create one if the user screws up
|
||||
if [ -n "$WINEPREFIX" ] && ! [ -f "$WINEPREFIX/system.reg" ]; then
|
||||
echo "$WINEPREFIX:"' Not a valid wine prefix.' >&2
|
||||
exit 1
|
||||
fi
|
||||
|
||||
# find wine executable
|
||||
export WINEDEBUG=-all
|
||||
# disable mscoree and mshtml to avoid downloading
|
||||
# wine gecko and mono
|
||||
export WINEDLLOVERRIDES="mscoree,mshtml="
|
||||
|
||||
wine="wine"
|
||||
wine64="wine64"
|
||||
wineboot="wineboot"
|
||||
|
||||
# $PATH is the way for user to control where wine is located (including custom Wine versions).
|
||||
# Pure 64-bit Wine (non Wow64) requries skipping 32-bit steps.
|
||||
# In such case, wine64 and winebooot will be present, but wine binary will be missing,
|
||||
# however it can be present in other PATHs, so it shouldn't be used, to avoid versions mixing.
|
||||
wine_path=$(dirname "$(which $wineboot)")
|
||||
wow64=true
|
||||
if ! [ -f "$wine_path/$wine" ]; then
|
||||
wine=$wine64
|
||||
wow64=false
|
||||
fi
|
||||
|
||||
# resolve 32-bit and 64-bit system32 path
|
||||
winever=$($wine --version | grep wine)
|
||||
if [ -z "$winever" ]; then
|
||||
echo "$wine:"' Not a wine executable. Check your $wine.' >&2
|
||||
exit 1
|
||||
fi
|
||||
|
||||
# ensure wine placeholder dlls are recreated
|
||||
# if they are missing
|
||||
$wineboot -u
|
||||
|
||||
win64_sys_path=$($wine64 winepath -u 'C:\windows\system32' 2> /dev/null)
|
||||
win64_sys_path="${win64_sys_path/$'\r'/}"
|
||||
if $wow64; then
|
||||
win32_sys_path=$($wine winepath -u 'C:\windows\system32' 2> /dev/null)
|
||||
win32_sys_path="${win32_sys_path/$'\r'/}"
|
||||
fi
|
||||
|
||||
if [ -z "$win32_sys_path" ] && [ -z "$win64_sys_path" ]; then
|
||||
echo 'Failed to resolve C:\windows\system32.' >&2
|
||||
exit 1
|
||||
fi
|
||||
|
||||
# create native dll override
|
||||
overrideDll() {
|
||||
$wine reg add 'HKEY_CURRENT_USER\Software\Wine\DllOverrides' /v $1 /d native /f >/dev/null 2>&1
|
||||
if [ $? -ne 0 ]; then
|
||||
echo -e "Failed to add override for $1"
|
||||
exit 1
|
||||
fi
|
||||
}
|
||||
|
||||
# remove dll override
|
||||
restoreDll() {
|
||||
$wine reg delete 'HKEY_CURRENT_USER\Software\Wine\DllOverrides' /v $1 /f > /dev/null 2>&1
|
||||
if [ $? -ne 0 ]; then
|
||||
echo "Failed to remove override for $1"
|
||||
fi
|
||||
}
|
||||
|
||||
# copy or link dxvk dll, back up original file
|
||||
installFile() {
|
||||
dstfile="${1}/${3}.dll"
|
||||
srcfile="${basedir}/${2}/${3}.dll"
|
||||
|
||||
if [ -f "${srcfile}.so" ]; then
|
||||
srcfile="${srcfile}.so"
|
||||
fi
|
||||
|
||||
if ! [ -f "${srcfile}" ]; then
|
||||
echo "${srcfile}: File not found. Skipping." >&2
|
||||
return 1
|
||||
fi
|
||||
|
||||
if [ -n "$1" ]; then
|
||||
if [ -f "${dstfile}" ] || [ -h "${dstfile}" ]; then
|
||||
if ! [ -f "${dstfile}.old" ]; then
|
||||
mv -v "${dstfile}" "${dstfile}.old"
|
||||
else
|
||||
rm -v "${dstfile}"
|
||||
fi
|
||||
$file_cmd "${srcfile}" "${dstfile}"
|
||||
else
|
||||
echo "${dstfile}: File not found in wine prefix" >&2
|
||||
return 1
|
||||
fi
|
||||
fi
|
||||
return 0
|
||||
}
|
||||
|
||||
# remove dxvk dll, restore original file
|
||||
uninstallFile() {
|
||||
dstfile="${1}/${3}.dll"
|
||||
srcfile="${basedir}/${2}/${3}.dll"
|
||||
|
||||
if [ -f "${srcfile}.so" ]; then
|
||||
srcfile="${srcfile}.so"
|
||||
fi
|
||||
|
||||
if ! [ -f "${srcfile}" ]; then
|
||||
echo "${srcfile}: File not found. Skipping." >&2
|
||||
return 1
|
||||
fi
|
||||
|
||||
if ! [ -f "${dstfile}" ] && ! [ -h "${dstfile}" ]; then
|
||||
echo "${dstfile}: File not found. Skipping." >&2
|
||||
return 1
|
||||
fi
|
||||
|
||||
if [ -f "${dstfile}.old" ]; then
|
||||
rm -v "${dstfile}"
|
||||
mv -v "${dstfile}.old" "${dstfile}"
|
||||
return 0
|
||||
else
|
||||
return 1
|
||||
fi
|
||||
}
|
||||
|
||||
install() {
|
||||
installFile "$win64_sys_path" "$dxvk_lib64" "$1"
|
||||
inst64_ret="$?"
|
||||
|
||||
inst32_ret=-1
|
||||
if $wow64; then
|
||||
installFile "$win32_sys_path" "$dxvk_lib32" "$1"
|
||||
inst32_ret="$?"
|
||||
fi
|
||||
|
||||
if (( ($inst32_ret == 0) || ($inst64_ret == 0) )); then
|
||||
overrideDll "$1"
|
||||
fi
|
||||
}
|
||||
|
||||
uninstall() {
|
||||
uninstallFile "$win64_sys_path" "$dxvk_lib64" "$1"
|
||||
uninst64_ret="$?"
|
||||
|
||||
uninst32_ret=-1
|
||||
if $wow64; then
|
||||
uninstallFile "$win32_sys_path" "$dxvk_lib32" "$1"
|
||||
uninst32_ret="$?"
|
||||
fi
|
||||
|
||||
if (( ($uninst32_ret == 0) || ($uninst64_ret == 0) )); then
|
||||
restoreDll "$1"
|
||||
fi
|
||||
}
|
||||
|
||||
# skip dxgi during install if not explicitly
|
||||
# enabled, but always try to uninstall it
|
||||
if $with_dxgi || [ "$action" == "uninstall" ]; then
|
||||
$action dxgi
|
||||
fi
|
||||
|
||||
$action d3d9
|
||||
|
||||
if $with_d3d10 || [ "$action" == "uninstall" ]; then
|
||||
$action d3d10
|
||||
$action d3d10_1
|
||||
fi
|
||||
|
||||
$action d3d10core
|
||||
$action d3d11
|
@ -1,29 +0,0 @@
|
||||
LIBRARY D3D10.DLL
|
||||
EXPORTS
|
||||
D3D10CreateDevice
|
||||
D3D10CreateDeviceAndSwapChain
|
||||
D3D10GetVertexShaderProfile
|
||||
D3D10GetGeometryShaderProfile
|
||||
D3D10GetPixelShaderProfile
|
||||
D3D10CreateBlob
|
||||
D3D10GetInputSignatureBlob
|
||||
D3D10GetOutputSignatureBlob
|
||||
D3D10ReflectShader
|
||||
D3D10CompileShader
|
||||
D3D10CreateEffectFromMemory
|
||||
D3D10CreateEffectPoolFromMemory
|
||||
D3D10CompileEffectFromMemory
|
||||
D3D10DisassembleEffect
|
||||
D3D10DisassembleShader
|
||||
D3D10PreprocessShader
|
||||
D3D10CreateStateBlock
|
||||
D3D10StateBlockMaskDifference
|
||||
D3D10StateBlockMaskDisableAll
|
||||
D3D10StateBlockMaskDisableCapture
|
||||
D3D10StateBlockMaskEnableAll
|
||||
D3D10StateBlockMaskEnableCapture
|
||||
D3D10StateBlockMaskGetSetting
|
||||
D3D10StateBlockMaskIntersect
|
||||
D3D10StateBlockMaskUnion
|
||||
D3D10GetVersion
|
||||
D3D10RegisterLayers
|
@ -1,29 +0,0 @@
|
||||
LIBRARY D3D10_1.DLL
|
||||
EXPORTS
|
||||
D3D10CreateDevice1
|
||||
D3D10CreateDeviceAndSwapChain1
|
||||
D3D10GetVertexShaderProfile
|
||||
D3D10GetGeometryShaderProfile
|
||||
D3D10GetPixelShaderProfile
|
||||
D3D10CreateBlob
|
||||
D3D10GetInputSignatureBlob
|
||||
D3D10GetOutputSignatureBlob
|
||||
D3D10ReflectShader
|
||||
D3D10CompileShader
|
||||
D3D10CreateEffectFromMemory
|
||||
D3D10CreateEffectPoolFromMemory
|
||||
D3D10CompileEffectFromMemory
|
||||
D3D10DisassembleEffect
|
||||
D3D10DisassembleShader
|
||||
D3D10PreprocessShader
|
||||
D3D10CreateStateBlock
|
||||
D3D10StateBlockMaskDifference
|
||||
D3D10StateBlockMaskDisableAll
|
||||
D3D10StateBlockMaskDisableCapture
|
||||
D3D10StateBlockMaskEnableAll
|
||||
D3D10StateBlockMaskEnableCapture
|
||||
D3D10StateBlockMaskGetSetting
|
||||
D3D10StateBlockMaskIntersect
|
||||
D3D10StateBlockMaskUnion
|
||||
D3D10GetVersion
|
||||
D3D10RegisterLayers
|
@ -9,10 +9,14 @@ extern "C" {
|
||||
HRESULT __stdcall D3D11CoreCreateDevice(
|
||||
IDXGIFactory* pFactory,
|
||||
IDXGIAdapter* pAdapter,
|
||||
D3D_DRIVER_TYPE DriverType,
|
||||
HMODULE Software,
|
||||
UINT Flags,
|
||||
const D3D_FEATURE_LEVEL* pFeatureLevels,
|
||||
UINT FeatureLevels,
|
||||
ID3D11Device** ppDevice);
|
||||
UINT SDKVersion,
|
||||
ID3D11Device** ppDevice,
|
||||
D3D_FEATURE_LEVEL* pFeatureLevel);
|
||||
|
||||
|
||||
DLLEXPORT HRESULT __stdcall D3D10CoreCreateDevice(
|
||||
@ -31,8 +35,8 @@ extern "C" {
|
||||
if (FAILED(hr))
|
||||
return hr;
|
||||
|
||||
hr = D3D11CoreCreateDevice(pFactory, pAdapter,
|
||||
Flags, &FeatureLevel, 1, &d3d11Device);
|
||||
hr = D3D11CoreCreateDevice(pFactory, pAdapter, D3D_DRIVER_TYPE_UNKNOWN,
|
||||
nullptr, Flags, &FeatureLevel, 1, D3D11_SDK_VERSION, &d3d11Device, nullptr);
|
||||
|
||||
if (FAILED(hr))
|
||||
return hr;
|
||||
|
@ -1,9 +0,0 @@
|
||||
#pragma once
|
||||
|
||||
#include "d3d10_include.h"
|
||||
|
||||
#ifdef _MSC_VER
|
||||
struct __declspec(uuid("0803425a-57f5-4dd6-9465-a87570834a08")) ID3D10StateBlock;
|
||||
#else
|
||||
__CRT_UUID_DECL(ID3D10StateBlock, 0x0803425a,0x57f5,0x4dd6,0x94,0x65,0xa8,0x75,0x70,0x83,0x4a,0x08);
|
||||
#endif
|
@ -1,335 +0,0 @@
|
||||
#include <d3dcompiler.h>
|
||||
|
||||
#include "d3d10_include.h"
|
||||
#include "d3d10_reflection.h"
|
||||
|
||||
#include "../dxgi/dxgi_adapter.h"
|
||||
|
||||
namespace dxvk {
|
||||
Logger Logger::s_instance("d3d10.log");
|
||||
}
|
||||
|
||||
extern "C" {
|
||||
using namespace dxvk;
|
||||
|
||||
HRESULT __stdcall D3D10CoreCreateDevice(
|
||||
IDXGIFactory* pFactory,
|
||||
IDXGIAdapter* pAdapter,
|
||||
UINT Flags,
|
||||
D3D_FEATURE_LEVEL FeatureLevel,
|
||||
ID3D10Device** ppDevice);
|
||||
|
||||
static HRESULT D3D10InternalCreateDeviceAndSwapChain(
|
||||
IDXGIAdapter* pAdapter,
|
||||
D3D10_DRIVER_TYPE DriverType,
|
||||
HMODULE Software,
|
||||
UINT Flags,
|
||||
D3D10_FEATURE_LEVEL1 HardwareLevel,
|
||||
UINT SDKVersion,
|
||||
DXGI_SWAP_CHAIN_DESC* pSwapChainDesc,
|
||||
IDXGISwapChain** ppSwapChain,
|
||||
REFIID deviceIID,
|
||||
void** ppDevice) {
|
||||
InitReturnPtr(ppDevice);
|
||||
InitReturnPtr(ppSwapChain);
|
||||
|
||||
if (ppSwapChain && !pSwapChainDesc)
|
||||
return E_INVALIDARG;
|
||||
|
||||
HRESULT hr;
|
||||
|
||||
// Get DXGI factory and adapter. This is mostly
|
||||
// copied from the equivalent D3D11 functions.
|
||||
Com<IDXGIFactory> dxgiFactory = nullptr;
|
||||
Com<IDXGIAdapter> dxgiAdapter = pAdapter;
|
||||
Com<ID3D10Device> device = nullptr;
|
||||
|
||||
if (!pAdapter) {
|
||||
if (DriverType != D3D10_DRIVER_TYPE_HARDWARE)
|
||||
Logger::warn("D3D10CreateDevice: Unsupported driver type");
|
||||
|
||||
hr = CreateDXGIFactory(__uuidof(IDXGIFactory), reinterpret_cast<void**>(&dxgiFactory));
|
||||
|
||||
if (FAILED(hr)) {
|
||||
Logger::err("D3D10CreateDevice: Failed to create a DXGI factory");
|
||||
return hr;
|
||||
}
|
||||
|
||||
hr = dxgiFactory->EnumAdapters(0, &dxgiAdapter);
|
||||
|
||||
if (FAILED(hr)) {
|
||||
Logger::err("D3D10CreateDevice: No default adapter available");
|
||||
return hr;
|
||||
}
|
||||
} else {
|
||||
if (FAILED(dxgiAdapter->GetParent(__uuidof(IDXGIFactory), reinterpret_cast<void**>(&dxgiFactory)))) {
|
||||
Logger::err("D3D10CreateDevice: Failed to query DXGI factory from DXGI adapter");
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
|
||||
if (DriverType != D3D10_DRIVER_TYPE_HARDWARE || Software)
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
|
||||
hr = D3D10CoreCreateDevice(
|
||||
dxgiFactory.ptr(), dxgiAdapter.ptr(),
|
||||
Flags, D3D_FEATURE_LEVEL(HardwareLevel),
|
||||
&device);
|
||||
|
||||
if (FAILED(hr))
|
||||
return hr;
|
||||
|
||||
if (ppSwapChain) {
|
||||
DXGI_SWAP_CHAIN_DESC desc = *pSwapChainDesc;
|
||||
hr = dxgiFactory->CreateSwapChain(device.ptr(), &desc, ppSwapChain);
|
||||
|
||||
if (FAILED(hr)) {
|
||||
Logger::err("D3D10CreateDevice: Failed to create swap chain");
|
||||
return hr;
|
||||
}
|
||||
}
|
||||
|
||||
if (ppDevice) {
|
||||
// Just assume that this succeeds
|
||||
device->QueryInterface(deviceIID, ppDevice);
|
||||
}
|
||||
|
||||
if (!ppDevice && !ppSwapChain)
|
||||
return S_FALSE;
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
DLLEXPORT HRESULT __stdcall D3D10CreateDevice(
|
||||
IDXGIAdapter* pAdapter,
|
||||
D3D10_DRIVER_TYPE DriverType,
|
||||
HMODULE Software,
|
||||
UINT Flags,
|
||||
UINT SDKVersion,
|
||||
ID3D10Device** ppDevice) {
|
||||
return D3D10InternalCreateDeviceAndSwapChain(
|
||||
pAdapter, DriverType, Software, Flags,
|
||||
D3D10_FEATURE_LEVEL_10_0, SDKVersion,
|
||||
nullptr, nullptr,
|
||||
__uuidof(ID3D10Device),
|
||||
reinterpret_cast<void**>(ppDevice));
|
||||
}
|
||||
|
||||
|
||||
DLLEXPORT HRESULT __stdcall D3D10CreateDevice1(
|
||||
IDXGIAdapter* pAdapter,
|
||||
D3D10_DRIVER_TYPE DriverType,
|
||||
HMODULE Software,
|
||||
UINT Flags,
|
||||
D3D10_FEATURE_LEVEL1 HardwareLevel,
|
||||
UINT SDKVersion,
|
||||
ID3D10Device1** ppDevice) {
|
||||
return D3D10InternalCreateDeviceAndSwapChain(
|
||||
pAdapter, DriverType, Software, Flags,
|
||||
HardwareLevel, SDKVersion,
|
||||
nullptr, nullptr,
|
||||
__uuidof(ID3D10Device1),
|
||||
reinterpret_cast<void**>(ppDevice));
|
||||
}
|
||||
|
||||
|
||||
DLLEXPORT HRESULT __stdcall D3D10CreateDeviceAndSwapChain(
|
||||
IDXGIAdapter* pAdapter,
|
||||
D3D10_DRIVER_TYPE DriverType,
|
||||
HMODULE Software,
|
||||
UINT Flags,
|
||||
UINT SDKVersion,
|
||||
DXGI_SWAP_CHAIN_DESC* pSwapChainDesc,
|
||||
IDXGISwapChain** ppSwapChain,
|
||||
ID3D10Device** ppDevice) {
|
||||
return D3D10InternalCreateDeviceAndSwapChain(
|
||||
pAdapter, DriverType, Software, Flags,
|
||||
D3D10_FEATURE_LEVEL_10_0, SDKVersion,
|
||||
pSwapChainDesc, ppSwapChain,
|
||||
__uuidof(ID3D10Device),
|
||||
reinterpret_cast<void**>(ppDevice));
|
||||
}
|
||||
|
||||
|
||||
DLLEXPORT HRESULT __stdcall D3D10CreateDeviceAndSwapChain1(
|
||||
IDXGIAdapter* pAdapter,
|
||||
D3D10_DRIVER_TYPE DriverType,
|
||||
HMODULE Software,
|
||||
UINT Flags,
|
||||
D3D10_FEATURE_LEVEL1 HardwareLevel,
|
||||
UINT SDKVersion,
|
||||
DXGI_SWAP_CHAIN_DESC* pSwapChainDesc,
|
||||
IDXGISwapChain** ppSwapChain,
|
||||
ID3D10Device1** ppDevice) {
|
||||
return D3D10InternalCreateDeviceAndSwapChain(
|
||||
pAdapter, DriverType, Software, Flags,
|
||||
HardwareLevel, SDKVersion,
|
||||
pSwapChainDesc, ppSwapChain,
|
||||
__uuidof(ID3D10Device1),
|
||||
reinterpret_cast<void**>(ppDevice));
|
||||
}
|
||||
|
||||
|
||||
const char* STDMETHODCALLTYPE D3D10GetVertexShaderProfile (ID3D10Device*) { return "vs_4_1"; }
|
||||
const char* STDMETHODCALLTYPE D3D10GetGeometryShaderProfile (ID3D10Device*) { return "gs_4_1"; }
|
||||
const char* STDMETHODCALLTYPE D3D10GetPixelShaderProfile (ID3D10Device*) { return "ps_4_1"; }
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10CreateBlob(SIZE_T size, LPD3D10BLOB* ppBuffer) {
|
||||
return D3DCreateBlob(size, ppBuffer);
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10GetInputSignatureBlob(
|
||||
const void* pShaderBytecode,
|
||||
SIZE_T BytecodeLength,
|
||||
ID3D10Blob** ppSignatureBlob) {
|
||||
return D3DGetInputSignatureBlob(
|
||||
pShaderBytecode,
|
||||
BytecodeLength,
|
||||
ppSignatureBlob);
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10GetOutputSignatureBlob(
|
||||
const void* pShaderBytecode,
|
||||
SIZE_T BytecodeLength,
|
||||
ID3D10Blob** ppSignatureBlob) {
|
||||
return D3DGetOutputSignatureBlob(
|
||||
pShaderBytecode,
|
||||
BytecodeLength,
|
||||
ppSignatureBlob);
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10ReflectShader(
|
||||
const void* pShaderBytecode,
|
||||
SIZE_T BytecodeLength,
|
||||
ID3D10ShaderReflection** ppReflector) {
|
||||
static const GUID IID_ID3D11ShaderReflection =
|
||||
{0x0a233719,0x3960,0x4578,{0x9d,0x7c,0x20,0x3b,0x8b,0x1d,0x9c,0xc1}};
|
||||
|
||||
InitReturnPtr(ppReflector);
|
||||
|
||||
Com<ID3D11ShaderReflection> d3d11Reflector = nullptr;
|
||||
|
||||
HRESULT hr = D3DReflect(pShaderBytecode,
|
||||
BytecodeLength, IID_ID3D11ShaderReflection,
|
||||
reinterpret_cast<void**>(&d3d11Reflector));
|
||||
|
||||
if (FAILED(hr)) {
|
||||
Logger::err("D3D10ReflectShader: Failed to create ID3D11ShaderReflection");
|
||||
return hr;
|
||||
}
|
||||
|
||||
*ppReflector = ref(new D3D10ShaderReflection(d3d11Reflector.ptr()));
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10CompileShader(
|
||||
LPCSTR pSrcData,
|
||||
SIZE_T SrcDataSize,
|
||||
LPCSTR pFileName,
|
||||
const D3D10_SHADER_MACRO* pDefines,
|
||||
LPD3D10INCLUDE pInclude,
|
||||
LPCSTR pFunctionName,
|
||||
LPCSTR pProfile,
|
||||
UINT Flags,
|
||||
ID3D10Blob** ppShader,
|
||||
ID3D10Blob** ppErrorMsgs) {
|
||||
return D3DCompile(pSrcData, SrcDataSize, pFileName,
|
||||
pDefines, pInclude, pFunctionName, pProfile, Flags,
|
||||
0, ppShader, ppErrorMsgs);
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10CreateEffectFromMemory(
|
||||
void* pData,
|
||||
SIZE_T DataSize,
|
||||
UINT EffectFlags,
|
||||
ID3D10Device* pDevice,
|
||||
ID3D10EffectPool* pEffectPool,
|
||||
ID3D10Effect** ppEffect) {
|
||||
Logger::warn("D3D10CreateEffectFromMemory: Not implemented");
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10CreateEffectPoolFromMemory(
|
||||
void* pData,
|
||||
SIZE_T DataSize,
|
||||
UINT EffectFlags,
|
||||
ID3D10Device* pDevice,
|
||||
ID3D10EffectPool** ppEffectPool) {
|
||||
Logger::warn("D3D10CreateEffectPoolFromMemory: Not implemented");
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10CompileEffectFromMemory(
|
||||
void* pData,
|
||||
SIZE_T DataLength,
|
||||
LPCSTR pSrcFileName,
|
||||
const D3D10_SHADER_MACRO* pDefines,
|
||||
ID3D10Include* pInclude,
|
||||
UINT ShaderFlags,
|
||||
UINT EffectFlags,
|
||||
ID3D10Blob** ppCompiledEffect,
|
||||
ID3D10Blob** ppErrors) {
|
||||
Logger::warn("D3D10CompileEffectFromMemory: Not implemented");
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10DisassembleEffect(
|
||||
ID3D10Effect* pEffect,
|
||||
BOOL EnableColorCode,
|
||||
ID3D10Blob** ppDisassembly) {
|
||||
Logger::warn("D3D10DisassembleEffect: Not implemented");
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10DisassembleShader(
|
||||
const void* pShader,
|
||||
SIZE_T BytecodeLength,
|
||||
BOOL EnableColorCode,
|
||||
LPCSTR pComments,
|
||||
ID3D10Blob** ppDisassembly) {
|
||||
return D3DDisassemble(
|
||||
pShader, BytecodeLength,
|
||||
0, pComments, ppDisassembly);
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10PreprocessShader(
|
||||
LPCSTR pSrcData,
|
||||
SIZE_T SrcDataSize,
|
||||
LPCSTR pFileName,
|
||||
const D3D10_SHADER_MACRO* pDefines,
|
||||
LPD3D10INCLUDE pInclude,
|
||||
ID3D10Blob** ppShaderText,
|
||||
ID3D10Blob** ppErrorMsgs) {
|
||||
return D3DPreprocess(
|
||||
pSrcData, SrcDataSize,
|
||||
pFileName, pDefines,
|
||||
pInclude,
|
||||
ppShaderText,
|
||||
ppErrorMsgs);
|
||||
}
|
||||
|
||||
|
||||
UINT64 STDMETHODCALLTYPE D3D10GetVersion() {
|
||||
return 0xa000100041770ull;
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10RegisterLayers() {
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
@ -6,9 +6,12 @@ namespace dxvk {
|
||||
|
||||
D3D10Multithread::D3D10Multithread(
|
||||
IUnknown* pParent,
|
||||
BOOL Protected)
|
||||
BOOL Protected,
|
||||
BOOL Force)
|
||||
: m_parent (pParent),
|
||||
m_protected (Protected) {
|
||||
m_protected (Protected || Force),
|
||||
m_enabled (Protected),
|
||||
m_forced (Force) {
|
||||
|
||||
}
|
||||
|
||||
@ -49,12 +52,18 @@ namespace dxvk {
|
||||
|
||||
BOOL STDMETHODCALLTYPE D3D10Multithread::SetMultithreadProtected(
|
||||
BOOL bMTProtect) {
|
||||
return std::exchange(m_protected, bMTProtect);
|
||||
BOOL result = m_enabled;
|
||||
m_enabled = bMTProtect;
|
||||
|
||||
if (!m_forced)
|
||||
m_protected = m_enabled;
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
BOOL STDMETHODCALLTYPE D3D10Multithread::GetMultithreadProtected() {
|
||||
return m_protected;
|
||||
return m_enabled;
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -64,7 +64,8 @@ namespace dxvk {
|
||||
|
||||
D3D10Multithread(
|
||||
IUnknown* pParent,
|
||||
BOOL Protected);
|
||||
BOOL Protected,
|
||||
BOOL Force);
|
||||
|
||||
~D3D10Multithread();
|
||||
|
||||
@ -95,6 +96,8 @@ namespace dxvk {
|
||||
|
||||
IUnknown* m_parent;
|
||||
BOOL m_protected;
|
||||
BOOL m_enabled;
|
||||
BOOL m_forced;
|
||||
|
||||
sync::RecursiveSpinlock m_mutex;
|
||||
|
||||
|
@ -6,7 +6,6 @@ namespace dxvk {
|
||||
|
||||
class D3D10Device;
|
||||
class D3D11Device;
|
||||
class D3D11DeviceContext;
|
||||
class D3D11Query;
|
||||
|
||||
class D3D10Query : public ID3D10Predicate {
|
||||
|
@ -1,326 +0,0 @@
|
||||
#include "d3d10_reflection.h"
|
||||
|
||||
namespace dxvk {
|
||||
|
||||
D3D10ShaderReflectionType::D3D10ShaderReflectionType(
|
||||
ID3D11ShaderReflectionType* d3d11)
|
||||
: m_d3d11(d3d11) {
|
||||
|
||||
}
|
||||
|
||||
|
||||
D3D10ShaderReflectionType::~D3D10ShaderReflectionType() {
|
||||
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10ShaderReflectionType::GetDesc(
|
||||
D3D10_SHADER_TYPE_DESC* pDesc) {
|
||||
D3D11_SHADER_TYPE_DESC d3d11Desc;
|
||||
HRESULT hr = m_d3d11->GetDesc(&d3d11Desc);
|
||||
|
||||
if (FAILED(hr))
|
||||
return hr;
|
||||
|
||||
pDesc->Class = D3D10_SHADER_VARIABLE_CLASS(d3d11Desc.Class);
|
||||
pDesc->Type = D3D10_SHADER_VARIABLE_TYPE (d3d11Desc.Type);
|
||||
pDesc->Rows = d3d11Desc.Rows;
|
||||
pDesc->Columns = d3d11Desc.Columns;
|
||||
pDesc->Elements = d3d11Desc.Elements;
|
||||
pDesc->Members = d3d11Desc.Members;
|
||||
pDesc->Offset = d3d11Desc.Offset;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
ID3D10ShaderReflectionType* STDMETHODCALLTYPE D3D10ShaderReflectionType::GetMemberTypeByIndex(
|
||||
UINT Index) {
|
||||
return FindMemberType(m_d3d11->GetMemberTypeByIndex(Index));
|
||||
}
|
||||
|
||||
|
||||
ID3D10ShaderReflectionType* STDMETHODCALLTYPE D3D10ShaderReflectionType::GetMemberTypeByName(
|
||||
const char* Name) {
|
||||
return FindMemberType(m_d3d11->GetMemberTypeByName(Name));
|
||||
}
|
||||
|
||||
|
||||
const char* STDMETHODCALLTYPE D3D10ShaderReflectionType::GetMemberTypeName(
|
||||
UINT Index) {
|
||||
return m_d3d11->GetMemberTypeName(Index);
|
||||
}
|
||||
|
||||
|
||||
ID3D10ShaderReflectionType* D3D10ShaderReflectionType::FindMemberType(
|
||||
ID3D11ShaderReflectionType* pMemberType) {
|
||||
if (!pMemberType)
|
||||
return nullptr;
|
||||
|
||||
auto entry = m_members.find(pMemberType);
|
||||
|
||||
if (entry == m_members.end()) {
|
||||
entry = m_members.insert({ pMemberType,
|
||||
std::make_unique<D3D10ShaderReflectionType>(pMemberType) }).first;
|
||||
}
|
||||
|
||||
return entry->second.get();
|
||||
}
|
||||
|
||||
|
||||
D3D10ShaderReflectionVariable::D3D10ShaderReflectionVariable(ID3D11ShaderReflectionVariable* d3d11)
|
||||
: m_d3d11(d3d11), m_type(m_d3d11->GetType()) {
|
||||
|
||||
}
|
||||
|
||||
|
||||
D3D10ShaderReflectionVariable::~D3D10ShaderReflectionVariable() {
|
||||
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10ShaderReflectionVariable::GetDesc(
|
||||
D3D10_SHADER_VARIABLE_DESC* pDesc) {
|
||||
D3D11_SHADER_VARIABLE_DESC d3d11Desc;
|
||||
HRESULT hr = m_d3d11->GetDesc(&d3d11Desc);
|
||||
|
||||
if (FAILED(hr))
|
||||
return hr;
|
||||
|
||||
pDesc->Name = d3d11Desc.Name;
|
||||
pDesc->StartOffset = d3d11Desc.StartOffset;
|
||||
pDesc->Size = d3d11Desc.Size;
|
||||
pDesc->uFlags = d3d11Desc.uFlags;
|
||||
pDesc->DefaultValue = d3d11Desc.DefaultValue;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
ID3D10ShaderReflectionType* STDMETHODCALLTYPE D3D10ShaderReflectionVariable::GetType() {
|
||||
return &m_type;
|
||||
}
|
||||
|
||||
|
||||
D3D10ShaderReflectionConstantBuffer::D3D10ShaderReflectionConstantBuffer(
|
||||
ID3D11ShaderReflectionConstantBuffer* d3d11)
|
||||
: m_d3d11(d3d11) {
|
||||
|
||||
}
|
||||
|
||||
|
||||
D3D10ShaderReflectionConstantBuffer::~D3D10ShaderReflectionConstantBuffer() {
|
||||
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10ShaderReflectionConstantBuffer::GetDesc(
|
||||
D3D10_SHADER_BUFFER_DESC* pDesc) {
|
||||
D3D11_SHADER_BUFFER_DESC d3d11Desc;
|
||||
HRESULT hr = m_d3d11->GetDesc(&d3d11Desc);
|
||||
|
||||
if (FAILED(hr))
|
||||
return hr;
|
||||
|
||||
pDesc->Name = d3d11Desc.Name;
|
||||
pDesc->Type = D3D10_CBUFFER_TYPE(d3d11Desc.Type);
|
||||
pDesc->Variables = d3d11Desc.Variables;
|
||||
pDesc->Size = d3d11Desc.Size;
|
||||
pDesc->uFlags = d3d11Desc.uFlags;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
ID3D10ShaderReflectionVariable* STDMETHODCALLTYPE D3D10ShaderReflectionConstantBuffer::GetVariableByIndex(
|
||||
UINT Index) {
|
||||
return FindVariable(m_d3d11->GetVariableByIndex(Index));
|
||||
}
|
||||
|
||||
|
||||
ID3D10ShaderReflectionVariable* STDMETHODCALLTYPE D3D10ShaderReflectionConstantBuffer::GetVariableByName(
|
||||
LPCSTR Name) {
|
||||
return FindVariable(m_d3d11->GetVariableByName(Name));
|
||||
}
|
||||
|
||||
|
||||
ID3D10ShaderReflectionVariable* D3D10ShaderReflectionConstantBuffer::FindVariable(
|
||||
ID3D11ShaderReflectionVariable* pVariable) {
|
||||
if (!pVariable)
|
||||
return nullptr;
|
||||
|
||||
auto entry = m_variables.find(pVariable);
|
||||
|
||||
if (entry == m_variables.end()) {
|
||||
entry = m_variables.emplace(
|
||||
std::piecewise_construct,
|
||||
std::forward_as_tuple(pVariable),
|
||||
std::forward_as_tuple(pVariable)).first;
|
||||
}
|
||||
|
||||
return &entry->second;
|
||||
}
|
||||
|
||||
|
||||
D3D10ShaderReflection::D3D10ShaderReflection(ID3D11ShaderReflection* d3d11)
|
||||
: m_d3d11(d3d11) {
|
||||
|
||||
}
|
||||
|
||||
|
||||
D3D10ShaderReflection::~D3D10ShaderReflection() {
|
||||
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10ShaderReflection::QueryInterface(
|
||||
REFIID riid,
|
||||
void** ppvObject) {
|
||||
if (ppvObject == nullptr)
|
||||
return E_POINTER;
|
||||
|
||||
static const GUID IID_ID3D10ShaderReflection
|
||||
= {0xd40e20b6,0xf8f7,0x42ad,{0xab,0x20,0x4b,0xaf,0x8f,0x15,0xdf,0xaa}};
|
||||
|
||||
if (riid == __uuidof(IUnknown)
|
||||
|| riid == IID_ID3D10ShaderReflection) {
|
||||
*ppvObject = ref(this);
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
return E_NOINTERFACE;
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10ShaderReflection::GetDesc(
|
||||
D3D10_SHADER_DESC* pDesc) {
|
||||
D3D11_SHADER_DESC d3d11Desc;
|
||||
HRESULT hr = m_d3d11->GetDesc(&d3d11Desc);
|
||||
|
||||
if (FAILED(hr))
|
||||
return hr;
|
||||
|
||||
pDesc->Version = d3d11Desc.Version;
|
||||
pDesc->Creator = d3d11Desc.Creator;
|
||||
pDesc->Flags = d3d11Desc.Flags;
|
||||
pDesc->ConstantBuffers = d3d11Desc.ConstantBuffers;
|
||||
pDesc->BoundResources = d3d11Desc.BoundResources;
|
||||
pDesc->InputParameters = d3d11Desc.InputParameters;
|
||||
pDesc->OutputParameters = d3d11Desc.OutputParameters;
|
||||
pDesc->InstructionCount = d3d11Desc.InstructionCount;
|
||||
pDesc->TempRegisterCount = d3d11Desc.TempRegisterCount;
|
||||
pDesc->TempArrayCount = d3d11Desc.TempArrayCount;
|
||||
pDesc->DefCount = d3d11Desc.DefCount;
|
||||
pDesc->DclCount = d3d11Desc.DclCount;
|
||||
pDesc->TextureNormalInstructions = d3d11Desc.TextureNormalInstructions;
|
||||
pDesc->TextureLoadInstructions = d3d11Desc.TextureLoadInstructions;
|
||||
pDesc->TextureCompInstructions = d3d11Desc.TextureCompInstructions;
|
||||
pDesc->TextureBiasInstructions = d3d11Desc.TextureBiasInstructions;
|
||||
pDesc->TextureGradientInstructions = d3d11Desc.TextureGradientInstructions;
|
||||
pDesc->FloatInstructionCount = d3d11Desc.FloatInstructionCount;
|
||||
pDesc->IntInstructionCount = d3d11Desc.IntInstructionCount;
|
||||
pDesc->UintInstructionCount = d3d11Desc.UintInstructionCount;
|
||||
pDesc->StaticFlowControlCount = d3d11Desc.StaticFlowControlCount;
|
||||
pDesc->DynamicFlowControlCount = d3d11Desc.DynamicFlowControlCount;
|
||||
pDesc->MacroInstructionCount = d3d11Desc.MacroInstructionCount;
|
||||
pDesc->ArrayInstructionCount = d3d11Desc.ArrayInstructionCount;
|
||||
pDesc->CutInstructionCount = d3d11Desc.CutInstructionCount;
|
||||
pDesc->EmitInstructionCount = d3d11Desc.EmitInstructionCount;
|
||||
pDesc->GSOutputTopology = D3D10_PRIMITIVE_TOPOLOGY(d3d11Desc.GSOutputTopology);
|
||||
pDesc->GSMaxOutputVertexCount = d3d11Desc.GSMaxOutputVertexCount;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
ID3D10ShaderReflectionConstantBuffer* STDMETHODCALLTYPE
|
||||
D3D10ShaderReflection::GetConstantBufferByIndex(
|
||||
UINT Index) {
|
||||
return FindConstantBuffer(m_d3d11->GetConstantBufferByIndex(Index));
|
||||
}
|
||||
|
||||
|
||||
ID3D10ShaderReflectionConstantBuffer* STDMETHODCALLTYPE
|
||||
D3D10ShaderReflection::GetConstantBufferByName(
|
||||
LPCSTR Name) {
|
||||
return FindConstantBuffer(m_d3d11->GetConstantBufferByName(Name));
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10ShaderReflection::GetInputParameterDesc(
|
||||
UINT ParameterIndex,
|
||||
D3D10_SIGNATURE_PARAMETER_DESC* pDesc) {
|
||||
D3D11_SIGNATURE_PARAMETER_DESC d3d11Desc;
|
||||
HRESULT hr = m_d3d11->GetInputParameterDesc(ParameterIndex, &d3d11Desc);
|
||||
|
||||
if (FAILED(hr))
|
||||
return hr;
|
||||
|
||||
ConvertSignatureParameterDesc(&d3d11Desc, pDesc);
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10ShaderReflection::GetOutputParameterDesc(
|
||||
UINT ParameterIndex,
|
||||
D3D10_SIGNATURE_PARAMETER_DESC* pDesc) {
|
||||
D3D11_SIGNATURE_PARAMETER_DESC d3d11Desc;
|
||||
HRESULT hr = m_d3d11->GetOutputParameterDesc(ParameterIndex, &d3d11Desc);
|
||||
|
||||
if (FAILED(hr))
|
||||
return hr;
|
||||
|
||||
ConvertSignatureParameterDesc(&d3d11Desc, pDesc);
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10ShaderReflection::GetResourceBindingDesc(
|
||||
UINT ResourceIndex,
|
||||
D3D10_SHADER_INPUT_BIND_DESC* pDesc) {
|
||||
D3D11_SHADER_INPUT_BIND_DESC d3d11Desc;
|
||||
HRESULT hr = m_d3d11->GetResourceBindingDesc(
|
||||
ResourceIndex, &d3d11Desc);
|
||||
|
||||
if (FAILED(hr))
|
||||
return hr;
|
||||
|
||||
pDesc->Name = d3d11Desc.Name;
|
||||
pDesc->Type = D3D10_SHADER_INPUT_TYPE(d3d11Desc.Type);
|
||||
pDesc->BindPoint = d3d11Desc.BindPoint;
|
||||
pDesc->BindCount = d3d11Desc.BindCount;
|
||||
pDesc->uFlags = d3d11Desc.uFlags;
|
||||
pDesc->ReturnType = D3D10_RESOURCE_RETURN_TYPE(d3d11Desc.ReturnType);
|
||||
pDesc->Dimension = D3D10_SRV_DIMENSION (d3d11Desc.Dimension);
|
||||
pDesc->NumSamples = d3d11Desc.NumSamples;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
ID3D10ShaderReflectionConstantBuffer* D3D10ShaderReflection::FindConstantBuffer(
|
||||
ID3D11ShaderReflectionConstantBuffer* pConstantBuffer) {
|
||||
if (!pConstantBuffer)
|
||||
return nullptr;
|
||||
|
||||
auto entry = m_constantBuffers.find(pConstantBuffer);
|
||||
|
||||
if (entry == m_constantBuffers.end()) {
|
||||
entry = m_constantBuffers.emplace(
|
||||
std::piecewise_construct,
|
||||
std::forward_as_tuple(pConstantBuffer),
|
||||
std::forward_as_tuple(pConstantBuffer)).first;
|
||||
}
|
||||
|
||||
return &entry->second;
|
||||
}
|
||||
|
||||
|
||||
void D3D10ShaderReflection::ConvertSignatureParameterDesc(
|
||||
const D3D11_SIGNATURE_PARAMETER_DESC* pSrcDesc,
|
||||
D3D10_SIGNATURE_PARAMETER_DESC* pDstDesc) {
|
||||
pDstDesc->SemanticName = pSrcDesc->SemanticName;
|
||||
pDstDesc->SemanticIndex = pSrcDesc->SemanticIndex;
|
||||
pDstDesc->Register = pSrcDesc->Register;
|
||||
pDstDesc->SystemValueType = D3D10_NAME(pSrcDesc->SystemValueType);
|
||||
pDstDesc->ComponentType = D3D10_REGISTER_COMPONENT_TYPE(pSrcDesc->ComponentType);
|
||||
pDstDesc->Mask = pSrcDesc->Mask;
|
||||
pDstDesc->ReadWriteMask = pSrcDesc->ReadWriteMask;
|
||||
}
|
||||
|
||||
}
|
@ -1,163 +0,0 @@
|
||||
#pragma once
|
||||
|
||||
#include <unordered_map>
|
||||
#include <vector>
|
||||
|
||||
#include "d3d10_include.h"
|
||||
|
||||
#include <d3d10shader.h>
|
||||
#include <d3d11shader.h>
|
||||
|
||||
namespace dxvk {
|
||||
|
||||
class D3D10ShaderReflectionType : public ID3D10ShaderReflectionType {
|
||||
|
||||
public:
|
||||
|
||||
D3D10ShaderReflectionType(
|
||||
ID3D11ShaderReflectionType* d3d11);
|
||||
|
||||
~D3D10ShaderReflectionType();
|
||||
|
||||
HRESULT STDMETHODCALLTYPE GetDesc(
|
||||
D3D10_SHADER_TYPE_DESC* pDesc);
|
||||
|
||||
ID3D10ShaderReflectionType* STDMETHODCALLTYPE GetMemberTypeByIndex(
|
||||
UINT Index);
|
||||
|
||||
ID3D10ShaderReflectionType* STDMETHODCALLTYPE GetMemberTypeByName(
|
||||
const char* Name);
|
||||
|
||||
const char* STDMETHODCALLTYPE GetMemberTypeName(
|
||||
UINT Index);
|
||||
|
||||
ID3D11ShaderReflectionType* GetD3D11Iface() {
|
||||
return m_d3d11;
|
||||
}
|
||||
|
||||
private:
|
||||
|
||||
ID3D11ShaderReflectionType* m_d3d11;
|
||||
|
||||
std::unordered_map<
|
||||
ID3D11ShaderReflectionType*,
|
||||
std::unique_ptr<D3D10ShaderReflectionType>> m_members;
|
||||
|
||||
ID3D10ShaderReflectionType* FindMemberType(
|
||||
ID3D11ShaderReflectionType* pMemberType);
|
||||
|
||||
};
|
||||
|
||||
|
||||
class D3D10ShaderReflectionVariable : public ID3D10ShaderReflectionVariable {
|
||||
|
||||
public:
|
||||
|
||||
D3D10ShaderReflectionVariable(
|
||||
ID3D11ShaderReflectionVariable* d3d11);
|
||||
|
||||
~D3D10ShaderReflectionVariable();
|
||||
|
||||
HRESULT STDMETHODCALLTYPE GetDesc(
|
||||
D3D10_SHADER_VARIABLE_DESC* pDesc);
|
||||
|
||||
ID3D10ShaderReflectionType* STDMETHODCALLTYPE GetType();
|
||||
|
||||
ID3D11ShaderReflectionVariable* STDMETHODCALLTYPE GetD3D11Iface() {
|
||||
return m_d3d11;
|
||||
}
|
||||
|
||||
private:
|
||||
|
||||
ID3D11ShaderReflectionVariable* m_d3d11;
|
||||
D3D10ShaderReflectionType m_type;
|
||||
|
||||
};
|
||||
|
||||
|
||||
class D3D10ShaderReflectionConstantBuffer : public ID3D10ShaderReflectionConstantBuffer {
|
||||
|
||||
public:
|
||||
|
||||
D3D10ShaderReflectionConstantBuffer(
|
||||
ID3D11ShaderReflectionConstantBuffer* d3d11);
|
||||
|
||||
~D3D10ShaderReflectionConstantBuffer();
|
||||
|
||||
HRESULT STDMETHODCALLTYPE GetDesc(
|
||||
D3D10_SHADER_BUFFER_DESC* pDesc);
|
||||
|
||||
ID3D10ShaderReflectionVariable* STDMETHODCALLTYPE GetVariableByIndex(
|
||||
UINT Index);
|
||||
|
||||
ID3D10ShaderReflectionVariable* STDMETHODCALLTYPE GetVariableByName(
|
||||
LPCSTR Name);
|
||||
|
||||
ID3D11ShaderReflectionConstantBuffer* STDMETHODCALLTYPE GetD3D11Iface() {
|
||||
return m_d3d11;
|
||||
}
|
||||
|
||||
private:
|
||||
|
||||
ID3D11ShaderReflectionConstantBuffer* m_d3d11;
|
||||
|
||||
std::unordered_map<
|
||||
ID3D11ShaderReflectionVariable*,
|
||||
D3D10ShaderReflectionVariable> m_variables;
|
||||
|
||||
ID3D10ShaderReflectionVariable* FindVariable(
|
||||
ID3D11ShaderReflectionVariable* pVariable);
|
||||
|
||||
};
|
||||
|
||||
|
||||
class D3D10ShaderReflection : public ComObject<ID3D10ShaderReflection> {
|
||||
|
||||
public:
|
||||
|
||||
D3D10ShaderReflection(ID3D11ShaderReflection* d3d11);
|
||||
~D3D10ShaderReflection();
|
||||
|
||||
HRESULT STDMETHODCALLTYPE QueryInterface(
|
||||
REFIID riid,
|
||||
void** ppvObject);
|
||||
|
||||
HRESULT STDMETHODCALLTYPE GetDesc(
|
||||
D3D10_SHADER_DESC* pDesc);
|
||||
|
||||
ID3D10ShaderReflectionConstantBuffer* STDMETHODCALLTYPE GetConstantBufferByIndex(
|
||||
UINT Index);
|
||||
|
||||
ID3D10ShaderReflectionConstantBuffer* STDMETHODCALLTYPE GetConstantBufferByName(
|
||||
LPCSTR Name);
|
||||
|
||||
HRESULT STDMETHODCALLTYPE GetInputParameterDesc(
|
||||
UINT ParameterIndex,
|
||||
D3D10_SIGNATURE_PARAMETER_DESC* pDesc);
|
||||
|
||||
HRESULT STDMETHODCALLTYPE GetOutputParameterDesc(
|
||||
UINT ParameterIndex,
|
||||
D3D10_SIGNATURE_PARAMETER_DESC* pDesc);
|
||||
|
||||
HRESULT STDMETHODCALLTYPE GetResourceBindingDesc(
|
||||
UINT ResourceIndex,
|
||||
D3D10_SHADER_INPUT_BIND_DESC* pDesc);
|
||||
|
||||
private:
|
||||
|
||||
Com<ID3D11ShaderReflection> m_d3d11;
|
||||
|
||||
std::unordered_map<
|
||||
ID3D11ShaderReflectionConstantBuffer*,
|
||||
D3D10ShaderReflectionConstantBuffer> m_constantBuffers;
|
||||
|
||||
ID3D10ShaderReflectionConstantBuffer* FindConstantBuffer(
|
||||
ID3D11ShaderReflectionConstantBuffer* pConstantBuffer);
|
||||
|
||||
void ConvertSignatureParameterDesc(
|
||||
const D3D11_SIGNATURE_PARAMETER_DESC* pSrcDesc,
|
||||
D3D10_SIGNATURE_PARAMETER_DESC* pDstDesc);
|
||||
|
||||
};
|
||||
|
||||
}
|
@ -1,432 +0,0 @@
|
||||
#include "d3d10_state_block.h"
|
||||
|
||||
#define MAKE_STATE_TYPE(field, count) { offsetof(D3D10_STATE_BLOCK_MASK, field), count }
|
||||
|
||||
namespace dxvk {
|
||||
|
||||
static const std::array<std::pair<size_t, size_t>, 24> g_stateTypes = {{
|
||||
MAKE_STATE_TYPE(SOBuffers, 1),
|
||||
MAKE_STATE_TYPE(OMRenderTargets, 1),
|
||||
MAKE_STATE_TYPE(OMDepthStencilState, 1),
|
||||
MAKE_STATE_TYPE(OMBlendState, 1),
|
||||
MAKE_STATE_TYPE(VS, 1),
|
||||
MAKE_STATE_TYPE(VSSamplers, D3D10_COMMONSHADER_SAMPLER_SLOT_COUNT),
|
||||
MAKE_STATE_TYPE(VSShaderResources, D3D10_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT),
|
||||
MAKE_STATE_TYPE(VSConstantBuffers, D3D10_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT),
|
||||
MAKE_STATE_TYPE(GS, 1),
|
||||
MAKE_STATE_TYPE(GSSamplers, D3D10_COMMONSHADER_SAMPLER_SLOT_COUNT),
|
||||
MAKE_STATE_TYPE(GSShaderResources, D3D10_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT),
|
||||
MAKE_STATE_TYPE(GSConstantBuffers, D3D10_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT),
|
||||
MAKE_STATE_TYPE(PS, 1),
|
||||
MAKE_STATE_TYPE(PSSamplers, D3D10_COMMONSHADER_SAMPLER_SLOT_COUNT),
|
||||
MAKE_STATE_TYPE(PSShaderResources, D3D10_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT),
|
||||
MAKE_STATE_TYPE(PSConstantBuffers, D3D10_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT),
|
||||
MAKE_STATE_TYPE(IAVertexBuffers, D3D10_IA_VERTEX_INPUT_RESOURCE_SLOT_COUNT),
|
||||
MAKE_STATE_TYPE(IAIndexBuffer, 1),
|
||||
MAKE_STATE_TYPE(IAInputLayout, 1),
|
||||
MAKE_STATE_TYPE(IAPrimitiveTopology, 1),
|
||||
MAKE_STATE_TYPE(RSViewports, 1),
|
||||
MAKE_STATE_TYPE(RSScissorRects, 1),
|
||||
MAKE_STATE_TYPE(RSRasterizerState, 1),
|
||||
MAKE_STATE_TYPE(Predication, 1),
|
||||
}};
|
||||
|
||||
|
||||
D3D10StateBlock::D3D10StateBlock(
|
||||
ID3D10Device* pDevice,
|
||||
const D3D10_STATE_BLOCK_MASK* pMask)
|
||||
: m_device(pDevice), m_mask(*pMask) {
|
||||
|
||||
}
|
||||
|
||||
|
||||
D3D10StateBlock::~D3D10StateBlock() {
|
||||
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10StateBlock::QueryInterface(
|
||||
REFIID riid,
|
||||
void** ppvObject) {
|
||||
if (ppvObject == nullptr)
|
||||
return E_POINTER;
|
||||
|
||||
*ppvObject = nullptr;
|
||||
|
||||
if (riid == __uuidof(IUnknown)
|
||||
|| riid == __uuidof(ID3D10StateBlock)) {
|
||||
*ppvObject = ref(this);
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
Logger::warn("D3D10StateBlock::QueryInterface: Unknown interface query");
|
||||
Logger::warn(str::format(riid));
|
||||
return E_NOINTERFACE;
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10StateBlock::Capture() {
|
||||
m_state = D3D10_STATE_BLOCK_STATE();
|
||||
|
||||
if (TestBit(&m_mask.VS, 0)) m_device->VSGetShader(&m_state.vs);
|
||||
if (TestBit(&m_mask.GS, 0)) m_device->GSGetShader(&m_state.gs);
|
||||
if (TestBit(&m_mask.PS, 0)) m_device->PSGetShader(&m_state.ps);
|
||||
|
||||
for (uint32_t i = 0; i < D3D10_COMMONSHADER_SAMPLER_SLOT_COUNT; i++) {
|
||||
if (TestBit(m_mask.VSSamplers, i)) m_device->VSGetSamplers(i, 1, &m_state.vsSso[i]);
|
||||
if (TestBit(m_mask.GSSamplers, i)) m_device->GSGetSamplers(i, 1, &m_state.gsSso[i]);
|
||||
if (TestBit(m_mask.PSSamplers, i)) m_device->PSGetSamplers(i, 1, &m_state.psSso[i]);
|
||||
}
|
||||
|
||||
for (uint32_t i = 0; i < D3D10_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT; i++) {
|
||||
if (TestBit(m_mask.VSShaderResources, i)) m_device->VSGetShaderResources(i, 1, &m_state.vsSrv[i]);
|
||||
if (TestBit(m_mask.GSShaderResources, i)) m_device->GSGetShaderResources(i, 1, &m_state.gsSrv[i]);
|
||||
if (TestBit(m_mask.PSShaderResources, i)) m_device->PSGetShaderResources(i, 1, &m_state.psSrv[i]);
|
||||
}
|
||||
|
||||
for (uint32_t i = 0; i < D3D10_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT; i++) {
|
||||
if (TestBit(m_mask.VSConstantBuffers, i)) m_device->VSGetConstantBuffers(i, 1, &m_state.vsCbo[i]);
|
||||
if (TestBit(m_mask.GSConstantBuffers, i)) m_device->GSGetConstantBuffers(i, 1, &m_state.gsCbo[i]);
|
||||
if (TestBit(m_mask.PSConstantBuffers, i)) m_device->PSGetConstantBuffers(i, 1, &m_state.psCbo[i]);
|
||||
}
|
||||
|
||||
for (uint32_t i = 0; i < D3D10_IA_VERTEX_INPUT_RESOURCE_SLOT_COUNT; i++) {
|
||||
if (TestBit(m_mask.IAVertexBuffers, i)) {
|
||||
m_device->IAGetVertexBuffers(i, 1,
|
||||
&m_state.iaVertexBuffers[i],
|
||||
&m_state.iaVertexOffsets[i],
|
||||
&m_state.iaVertexStrides[i]);
|
||||
}
|
||||
}
|
||||
|
||||
if (TestBit(&m_mask.IAIndexBuffer, 0)) {
|
||||
m_device->IAGetIndexBuffer(
|
||||
&m_state.iaIndexBuffer,
|
||||
&m_state.iaIndexFormat,
|
||||
&m_state.iaIndexOffset);
|
||||
}
|
||||
|
||||
if (TestBit(&m_mask.IAInputLayout, 0))
|
||||
m_device->IAGetInputLayout(&m_state.iaInputLayout);
|
||||
|
||||
if (TestBit(&m_mask.IAPrimitiveTopology, 0))
|
||||
m_device->IAGetPrimitiveTopology(&m_state.iaTopology);
|
||||
|
||||
if (TestBit(&m_mask.OMRenderTargets, 0)) {
|
||||
m_device->OMGetRenderTargets(
|
||||
D3D10_SIMULTANEOUS_RENDER_TARGET_COUNT,
|
||||
&m_state.omRtv[0], &m_state.omDsv);
|
||||
}
|
||||
|
||||
if (TestBit(&m_mask.OMDepthStencilState, 0)) {
|
||||
m_device->OMGetDepthStencilState(
|
||||
&m_state.omDepthStencilState,
|
||||
&m_state.omStencilRef);
|
||||
}
|
||||
|
||||
if (TestBit(&m_mask.OMBlendState, 0)) {
|
||||
m_device->OMGetBlendState(
|
||||
&m_state.omBlendState,
|
||||
m_state.omBlendFactor,
|
||||
&m_state.omSampleMask);
|
||||
}
|
||||
|
||||
if (TestBit(&m_mask.RSViewports, 0)) {
|
||||
m_device->RSGetViewports(&m_state.rsViewportCount, nullptr);
|
||||
m_device->RSGetViewports(&m_state.rsViewportCount, m_state.rsViewports);
|
||||
}
|
||||
|
||||
if (TestBit(&m_mask.RSScissorRects, 0)) {
|
||||
m_device->RSGetScissorRects(&m_state.rsScissorCount, nullptr);
|
||||
m_device->RSGetScissorRects(&m_state.rsScissorCount, m_state.rsScissors);
|
||||
}
|
||||
|
||||
if (TestBit(&m_mask.RSRasterizerState, 0))
|
||||
m_device->RSGetState(&m_state.rsState);
|
||||
|
||||
if (TestBit(&m_mask.SOBuffers, 0)) {
|
||||
m_device->SOGetTargets(
|
||||
D3D10_SO_BUFFER_SLOT_COUNT,
|
||||
&m_state.soBuffers[0],
|
||||
&m_state.soOffsets[0]);
|
||||
}
|
||||
|
||||
if (TestBit(&m_mask.Predication, 0))
|
||||
m_device->GetPredication(&m_state.predicate, &m_state.predicateInvert);
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10StateBlock::Apply() {
|
||||
if (TestBit(&m_mask.VS, 0)) m_device->VSSetShader(m_state.vs.ptr());
|
||||
if (TestBit(&m_mask.GS, 0)) m_device->GSSetShader(m_state.gs.ptr());
|
||||
if (TestBit(&m_mask.PS, 0)) m_device->PSSetShader(m_state.ps.ptr());
|
||||
|
||||
for (uint32_t i = 0; i < D3D10_COMMONSHADER_SAMPLER_SLOT_COUNT; i++) {
|
||||
if (TestBit(m_mask.VSSamplers, i)) m_device->VSSetSamplers(i, 1, &m_state.vsSso[i]);
|
||||
if (TestBit(m_mask.GSSamplers, i)) m_device->GSSetSamplers(i, 1, &m_state.gsSso[i]);
|
||||
if (TestBit(m_mask.PSSamplers, i)) m_device->PSSetSamplers(i, 1, &m_state.psSso[i]);
|
||||
}
|
||||
|
||||
for (uint32_t i = 0; i < D3D10_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT; i++) {
|
||||
if (TestBit(m_mask.VSShaderResources, i)) m_device->VSSetShaderResources(i, 1, &m_state.vsSrv[i]);
|
||||
if (TestBit(m_mask.GSShaderResources, i)) m_device->GSSetShaderResources(i, 1, &m_state.gsSrv[i]);
|
||||
if (TestBit(m_mask.PSShaderResources, i)) m_device->PSSetShaderResources(i, 1, &m_state.psSrv[i]);
|
||||
}
|
||||
|
||||
for (uint32_t i = 0; i < D3D10_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT; i++) {
|
||||
if (TestBit(m_mask.VSConstantBuffers, i)) m_device->VSSetConstantBuffers(i, 1, &m_state.vsCbo[i]);
|
||||
if (TestBit(m_mask.GSConstantBuffers, i)) m_device->GSSetConstantBuffers(i, 1, &m_state.gsCbo[i]);
|
||||
if (TestBit(m_mask.PSConstantBuffers, i)) m_device->PSSetConstantBuffers(i, 1, &m_state.psCbo[i]);
|
||||
}
|
||||
|
||||
for (uint32_t i = 0; i < D3D10_IA_VERTEX_INPUT_RESOURCE_SLOT_COUNT; i++) {
|
||||
if (TestBit(m_mask.IAVertexBuffers, i)) {
|
||||
m_device->IASetVertexBuffers(i, 1,
|
||||
&m_state.iaVertexBuffers[i],
|
||||
&m_state.iaVertexOffsets[i],
|
||||
&m_state.iaVertexStrides[i]);
|
||||
}
|
||||
}
|
||||
|
||||
if (TestBit(&m_mask.IAIndexBuffer, 0)) {
|
||||
m_device->IASetIndexBuffer(
|
||||
m_state.iaIndexBuffer.ptr(),
|
||||
m_state.iaIndexFormat,
|
||||
m_state.iaIndexOffset);
|
||||
}
|
||||
|
||||
if (TestBit(&m_mask.IAInputLayout, 0))
|
||||
m_device->IASetInputLayout(m_state.iaInputLayout.ptr());
|
||||
|
||||
if (TestBit(&m_mask.IAPrimitiveTopology, 0))
|
||||
m_device->IASetPrimitiveTopology(m_state.iaTopology);
|
||||
|
||||
if (TestBit(&m_mask.OMRenderTargets, 0)) {
|
||||
m_device->OMSetRenderTargets(
|
||||
D3D10_SIMULTANEOUS_RENDER_TARGET_COUNT,
|
||||
&m_state.omRtv[0], m_state.omDsv.ptr());
|
||||
}
|
||||
|
||||
if (TestBit(&m_mask.OMDepthStencilState, 0)) {
|
||||
m_device->OMSetDepthStencilState(
|
||||
m_state.omDepthStencilState.ptr(),
|
||||
m_state.omStencilRef);
|
||||
}
|
||||
|
||||
if (TestBit(&m_mask.OMBlendState, 0)) {
|
||||
m_device->OMSetBlendState(
|
||||
m_state.omBlendState.ptr(),
|
||||
m_state.omBlendFactor,
|
||||
m_state.omSampleMask);
|
||||
}
|
||||
|
||||
if (TestBit(&m_mask.RSViewports, 0))
|
||||
m_device->RSSetViewports(m_state.rsViewportCount, m_state.rsViewports);
|
||||
|
||||
if (TestBit(&m_mask.RSScissorRects, 0))
|
||||
m_device->RSSetScissorRects(m_state.rsScissorCount, m_state.rsScissors);
|
||||
|
||||
if (TestBit(&m_mask.RSRasterizerState, 0))
|
||||
m_device->RSSetState(m_state.rsState.ptr());
|
||||
|
||||
if (TestBit(&m_mask.SOBuffers, 0)) {
|
||||
m_device->SOSetTargets(
|
||||
D3D10_SO_BUFFER_SLOT_COUNT,
|
||||
&m_state.soBuffers[0],
|
||||
&m_state.soOffsets[0]);
|
||||
}
|
||||
|
||||
if (TestBit(&m_mask.Predication, 0))
|
||||
m_device->SetPredication(m_state.predicate.ptr(), m_state.predicateInvert);
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10StateBlock::GetDevice(
|
||||
ID3D10Device** ppDevice) {
|
||||
Logger::err("D3D10StateBlock::GetDevice: Stub");
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10StateBlock::ReleaseAllDeviceObjects() {
|
||||
// Not entirely sure if this is correct?
|
||||
m_state = D3D10_STATE_BLOCK_STATE();
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
BOOL D3D10StateBlock::TestBit(
|
||||
const BYTE* pMask,
|
||||
UINT Idx) {
|
||||
uint32_t byte = Idx / 8;
|
||||
uint32_t bit = Idx % 8;
|
||||
return (pMask[byte] & (1 << bit)) != 0;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
extern "C" {
|
||||
using namespace dxvk;
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10CreateStateBlock(
|
||||
ID3D10Device* pDevice,
|
||||
D3D10_STATE_BLOCK_MASK* pStateBlockMask,
|
||||
ID3D10StateBlock** ppStateBlock) {
|
||||
InitReturnPtr(ppStateBlock);
|
||||
|
||||
if (!pDevice || !pStateBlockMask || !ppStateBlock)
|
||||
return E_INVALIDARG;
|
||||
|
||||
*ppStateBlock = ref(new D3D10StateBlock(pDevice, pStateBlockMask));
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10StateBlockMaskEnableCapture(
|
||||
D3D10_STATE_BLOCK_MASK* pMask,
|
||||
D3D10_DEVICE_STATE_TYPES StateType,
|
||||
UINT StartIdx,
|
||||
UINT Count) {
|
||||
if (!pMask || !StateType || StateType > g_stateTypes.size())
|
||||
return E_INVALIDARG;
|
||||
|
||||
auto pair = g_stateTypes[uint32_t(StateType) - 1];
|
||||
auto mask = reinterpret_cast<BYTE*>(pMask) + pair.first;
|
||||
|
||||
if (StartIdx + Count > pair.second)
|
||||
return E_INVALIDARG;
|
||||
|
||||
for (uint32_t i = StartIdx; i < StartIdx + Count; i++) {
|
||||
uint32_t byte = i / 8;
|
||||
uint32_t bit = i % 8;
|
||||
mask[byte] |= 1 << bit;
|
||||
}
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10StateBlockMaskDisableCapture(
|
||||
D3D10_STATE_BLOCK_MASK* pMask,
|
||||
D3D10_DEVICE_STATE_TYPES StateType,
|
||||
UINT StartIdx,
|
||||
UINT Count) {
|
||||
if (!pMask || !StateType || StateType > g_stateTypes.size())
|
||||
return E_INVALIDARG;
|
||||
|
||||
auto pair = g_stateTypes[uint32_t(StateType) - 1];
|
||||
auto mask = reinterpret_cast<BYTE*>(pMask) + pair.first;
|
||||
|
||||
if (StartIdx + Count > pair.second)
|
||||
return E_INVALIDARG;
|
||||
|
||||
for (uint32_t i = StartIdx; i < StartIdx + Count; i++) {
|
||||
uint32_t byte = i / 8;
|
||||
uint32_t bit = i % 8;
|
||||
mask[byte] &= ~(1 << bit);
|
||||
}
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10StateBlockMaskEnableAll(
|
||||
D3D10_STATE_BLOCK_MASK* pMask) {
|
||||
if (!pMask)
|
||||
return E_INVALIDARG;
|
||||
|
||||
*pMask = D3D10_STATE_BLOCK_MASK();
|
||||
for (size_t i = 0; i < g_stateTypes.size(); i++) {
|
||||
D3D10StateBlockMaskEnableCapture(pMask,
|
||||
D3D10_DEVICE_STATE_TYPES(i + 1),
|
||||
0, g_stateTypes[i].second);
|
||||
}
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10StateBlockMaskDisableAll(
|
||||
D3D10_STATE_BLOCK_MASK* pMask) {
|
||||
if (!pMask)
|
||||
return E_INVALIDARG;
|
||||
|
||||
*pMask = D3D10_STATE_BLOCK_MASK();
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
BOOL STDMETHODCALLTYPE D3D10StateBlockMaskGetSetting(
|
||||
D3D10_STATE_BLOCK_MASK* pMask,
|
||||
D3D10_DEVICE_STATE_TYPES StateType,
|
||||
UINT Idx) {
|
||||
if (!pMask || !StateType || StateType > g_stateTypes.size())
|
||||
return FALSE;
|
||||
|
||||
auto pair = g_stateTypes[uint32_t(StateType) - 1];
|
||||
auto mask = reinterpret_cast<BYTE*>(pMask) + pair.first;
|
||||
|
||||
if (Idx >= pair.second)
|
||||
return FALSE;
|
||||
|
||||
uint32_t byte = Idx / 8;
|
||||
uint32_t bit = Idx % 8;
|
||||
return (mask[byte] & (1 << bit)) != 0;
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10StateBlockMaskDifference(
|
||||
D3D10_STATE_BLOCK_MASK* pA,
|
||||
D3D10_STATE_BLOCK_MASK* pB,
|
||||
D3D10_STATE_BLOCK_MASK* pResult) {
|
||||
if (!pA || !pB || !pResult)
|
||||
return E_INVALIDARG;
|
||||
|
||||
auto a = reinterpret_cast<const BYTE*>(pA);
|
||||
auto b = reinterpret_cast<const BYTE*>(pB);
|
||||
auto r = reinterpret_cast<BYTE*>(pResult);
|
||||
|
||||
for (size_t i = 0; i < sizeof(D3D10_STATE_BLOCK_MASK); i++)
|
||||
r[i] = a[i] ^ b[i];
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10StateBlockMaskIntersect(
|
||||
D3D10_STATE_BLOCK_MASK* pA,
|
||||
D3D10_STATE_BLOCK_MASK* pB,
|
||||
D3D10_STATE_BLOCK_MASK* pResult) {
|
||||
if (!pA || !pB || !pResult)
|
||||
return E_INVALIDARG;
|
||||
|
||||
auto a = reinterpret_cast<const BYTE*>(pA);
|
||||
auto b = reinterpret_cast<const BYTE*>(pB);
|
||||
auto r = reinterpret_cast<BYTE*>(pResult);
|
||||
|
||||
for (size_t i = 0; i < sizeof(D3D10_STATE_BLOCK_MASK); i++)
|
||||
r[i] = a[i] & b[i];
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D10StateBlockMaskUnion(
|
||||
D3D10_STATE_BLOCK_MASK* pA,
|
||||
D3D10_STATE_BLOCK_MASK* pB,
|
||||
D3D10_STATE_BLOCK_MASK* pResult) {
|
||||
if (!pA || !pB || !pResult)
|
||||
return E_INVALIDARG;
|
||||
|
||||
auto a = reinterpret_cast<const BYTE*>(pA);
|
||||
auto b = reinterpret_cast<const BYTE*>(pB);
|
||||
auto r = reinterpret_cast<BYTE*>(pResult);
|
||||
|
||||
for (size_t i = 0; i < sizeof(D3D10_STATE_BLOCK_MASK); i++)
|
||||
r[i] = a[i] | b[i];
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
}
|
@ -1,82 +0,0 @@
|
||||
#pragma once
|
||||
|
||||
#include "d3d10_include.h"
|
||||
#include "d3d10_interfaces.h"
|
||||
|
||||
namespace dxvk {
|
||||
|
||||
struct D3D10_STATE_BLOCK_STATE {
|
||||
Com<ID3D10VertexShader> vs = { };
|
||||
Com<ID3D10SamplerState> vsSso[D3D10_COMMONSHADER_SAMPLER_SLOT_COUNT] = { };
|
||||
Com<ID3D10ShaderResourceView> vsSrv[D3D10_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT] = { };
|
||||
Com<ID3D10Buffer> vsCbo[D3D10_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT] = { };
|
||||
Com<ID3D10GeometryShader> gs = { };
|
||||
Com<ID3D10SamplerState> gsSso[D3D10_COMMONSHADER_SAMPLER_SLOT_COUNT] = { };
|
||||
Com<ID3D10ShaderResourceView> gsSrv[D3D10_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT] = { };
|
||||
Com<ID3D10Buffer> gsCbo[D3D10_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT] = { };
|
||||
Com<ID3D10PixelShader> ps = { };
|
||||
Com<ID3D10SamplerState> psSso[D3D10_COMMONSHADER_SAMPLER_SLOT_COUNT] = { };
|
||||
Com<ID3D10ShaderResourceView> psSrv[D3D10_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT] = { };
|
||||
Com<ID3D10Buffer> psCbo[D3D10_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT] = { };
|
||||
Com<ID3D10Buffer> iaVertexBuffers[D3D10_IA_VERTEX_INPUT_RESOURCE_SLOT_COUNT] = { };
|
||||
UINT iaVertexOffsets[D3D10_IA_VERTEX_INPUT_RESOURCE_SLOT_COUNT] = { };
|
||||
UINT iaVertexStrides[D3D10_IA_VERTEX_INPUT_RESOURCE_SLOT_COUNT] = { };
|
||||
Com<ID3D10Buffer> iaIndexBuffer = { };
|
||||
DXGI_FORMAT iaIndexFormat = DXGI_FORMAT_UNKNOWN;
|
||||
UINT iaIndexOffset = 0;
|
||||
Com<ID3D10InputLayout> iaInputLayout = nullptr;
|
||||
D3D10_PRIMITIVE_TOPOLOGY iaTopology = D3D10_PRIMITIVE_TOPOLOGY_UNDEFINED;
|
||||
Com<ID3D10RenderTargetView> omRtv[D3D10_SIMULTANEOUS_RENDER_TARGET_COUNT] = { };
|
||||
Com<ID3D10DepthStencilView> omDsv = { };
|
||||
Com<ID3D10DepthStencilState> omDepthStencilState = { };
|
||||
UINT omStencilRef = 0;
|
||||
Com<ID3D10BlendState> omBlendState = { };
|
||||
FLOAT omBlendFactor[4] = { };
|
||||
UINT omSampleMask = 0;
|
||||
UINT rsViewportCount = 0;
|
||||
D3D10_VIEWPORT rsViewports[D3D10_VIEWPORT_AND_SCISSORRECT_OBJECT_COUNT_PER_PIPELINE] = { };
|
||||
UINT rsScissorCount = 0;
|
||||
RECT rsScissors [D3D10_VIEWPORT_AND_SCISSORRECT_OBJECT_COUNT_PER_PIPELINE] = { };
|
||||
Com<ID3D10RasterizerState> rsState = { };
|
||||
Com<ID3D10Buffer> soBuffers[D3D10_SO_BUFFER_SLOT_COUNT] = { };
|
||||
UINT soOffsets[D3D10_SO_BUFFER_SLOT_COUNT] = { };
|
||||
Com<ID3D10Predicate> predicate = { };
|
||||
BOOL predicateInvert = FALSE;
|
||||
};
|
||||
|
||||
|
||||
class D3D10StateBlock : public ComObject<ID3D10StateBlock> {
|
||||
|
||||
public:
|
||||
D3D10StateBlock(
|
||||
ID3D10Device* pDevice,
|
||||
const D3D10_STATE_BLOCK_MASK* pMask);
|
||||
|
||||
~D3D10StateBlock();
|
||||
|
||||
HRESULT STDMETHODCALLTYPE QueryInterface(
|
||||
REFIID riid,
|
||||
void** ppvObject);
|
||||
|
||||
HRESULT STDMETHODCALLTYPE Capture();
|
||||
|
||||
HRESULT STDMETHODCALLTYPE Apply();
|
||||
|
||||
HRESULT STDMETHODCALLTYPE GetDevice(
|
||||
ID3D10Device** ppDevice);
|
||||
|
||||
HRESULT STDMETHODCALLTYPE ReleaseAllDeviceObjects();
|
||||
|
||||
private:
|
||||
|
||||
Com<ID3D10Device> m_device;
|
||||
D3D10_STATE_BLOCK_MASK m_mask;
|
||||
D3D10_STATE_BLOCK_STATE m_state;
|
||||
|
||||
static BOOL TestBit(
|
||||
const BYTE* pMask,
|
||||
UINT Idx);
|
||||
|
||||
};
|
||||
|
||||
}
|
9
src/d3d10/d3d10core.sym
Normal file
9
src/d3d10/d3d10core.sym
Normal file
@ -0,0 +1,9 @@
|
||||
{
|
||||
global:
|
||||
D3D10CoreCreateDevice;
|
||||
D3D10CoreGetVersion;
|
||||
D3D10CoreRegisterLayers;
|
||||
|
||||
local:
|
||||
*;
|
||||
};
|
@ -1,48 +1,30 @@
|
||||
d3d10_res = wrc_generator.process('version10.rc')
|
||||
d3d10_1_res = wrc_generator.process('version10_1.rc')
|
||||
d3d10_core_res = wrc_generator.process('version10_core.rc')
|
||||
|
||||
d3d10_core_src = [
|
||||
'd3d10_core.cpp',
|
||||
]
|
||||
|
||||
d3d10_main_src = [
|
||||
'd3d10_main.cpp',
|
||||
'd3d10_reflection.cpp',
|
||||
'd3d10_state_block.cpp',
|
||||
]
|
||||
d3d10_core_ld_args = []
|
||||
d3d10_core_link_depends = []
|
||||
|
||||
if platform == 'windows'
|
||||
d3d10_d3d11_dep = lib_d3d11
|
||||
else
|
||||
d3d10_core_ld_args += [ '-Wl,--version-script', join_paths(meson.current_source_dir(), 'd3d10core.sym') ]
|
||||
d3d10_core_link_depends += files('d3d10core.sym')
|
||||
d3d10_d3d11_dep = d3d11_dep
|
||||
endif
|
||||
|
||||
d3d10_core_dll = shared_library('d3d10core'+dll_ext, d3d10_core_src, d3d10_core_res,
|
||||
name_prefix : '',
|
||||
dependencies : [ d3d11_dep ],
|
||||
name_prefix : dxvk_name_prefix,
|
||||
dependencies : [ d3d10_d3d11_dep ],
|
||||
include_directories : dxvk_include_path,
|
||||
install : true,
|
||||
vs_module_defs : 'd3d10core'+def_spec_ext,
|
||||
link_args : d3d10_core_ld_args,
|
||||
link_depends : [ d3d10_core_link_depends ],
|
||||
)
|
||||
|
||||
d3d10_core_dep = declare_dependency(
|
||||
link_with : [ d3d10_core_dll ],
|
||||
)
|
||||
|
||||
d3d10_deps = [ lib_d3dcompiler_43, lib_dxgi, dxbc_dep, dxvk_dep, d3d10_core_dep ]
|
||||
|
||||
d3d10_dll = shared_library('d3d10'+dll_ext, d3d10_main_src, d3d10_res,
|
||||
name_prefix : '',
|
||||
dependencies : [ d3d10_deps ],
|
||||
include_directories : dxvk_include_path,
|
||||
install : true,
|
||||
vs_module_defs : 'd3d10'+def_spec_ext,
|
||||
)
|
||||
|
||||
d3d10_1_dll = shared_library('d3d10_1'+dll_ext, d3d10_main_src, d3d10_1_res,
|
||||
name_prefix : '',
|
||||
dependencies : [ d3d10_deps ],
|
||||
include_directories : dxvk_include_path,
|
||||
install : true,
|
||||
vs_module_defs : 'd3d10_1'+def_spec_ext,
|
||||
)
|
||||
|
||||
d3d10_dep = declare_dependency(
|
||||
link_with : [ d3d10_dll, d3d10_1_dll, d3d10_core_dll ],
|
||||
include_directories : [ dxvk_include_path ],
|
||||
)
|
||||
|
@ -1,32 +0,0 @@
|
||||
#include <windows.h>
|
||||
|
||||
// DLL version information.
|
||||
VS_VERSION_INFO VERSIONINFO
|
||||
FILEVERSION 10,0,17763,1
|
||||
PRODUCTVERSION 10,0,17763,1
|
||||
FILEFLAGSMASK VS_FFI_FILEFLAGSMASK
|
||||
FILEFLAGS 0
|
||||
FILEOS VOS_NT_WINDOWS32
|
||||
FILETYPE VFT_DLL
|
||||
FILESUBTYPE VFT2_UNKNOWN
|
||||
BEGIN
|
||||
BLOCK "StringFileInfo"
|
||||
BEGIN
|
||||
BLOCK "080904b0"
|
||||
BEGIN
|
||||
VALUE "CompanyName", "DXVK"
|
||||
VALUE "FileDescription", "Direct3D 10 Runtime"
|
||||
VALUE "FileVersion", "10.0.17763.1 (WinBuild.160101.0800)"
|
||||
VALUE "InternalName", "D3D10.dll"
|
||||
VALUE "LegalCopyright", "zlib/libpng license"
|
||||
VALUE "OriginalFilename", "D3D10.dll"
|
||||
VALUE "ProductName", "DXVK"
|
||||
VALUE "ProductVersion", "10.0.17763.1"
|
||||
END
|
||||
END
|
||||
BLOCK "VarFileInfo"
|
||||
BEGIN
|
||||
VALUE "Translation", 0x0809, 1200
|
||||
END
|
||||
END
|
||||
|
@ -1,32 +0,0 @@
|
||||
#include <windows.h>
|
||||
|
||||
// DLL version information.
|
||||
VS_VERSION_INFO VERSIONINFO
|
||||
FILEVERSION 10,0,17763,1
|
||||
PRODUCTVERSION 10,0,17763,1
|
||||
FILEFLAGSMASK VS_FFI_FILEFLAGSMASK
|
||||
FILEFLAGS 0
|
||||
FILEOS VOS_NT_WINDOWS32
|
||||
FILETYPE VFT_DLL
|
||||
FILESUBTYPE VFT2_UNKNOWN
|
||||
BEGIN
|
||||
BLOCK "StringFileInfo"
|
||||
BEGIN
|
||||
BLOCK "080904b0"
|
||||
BEGIN
|
||||
VALUE "CompanyName", "DXVK"
|
||||
VALUE "FileDescription", "Direct3D 10.1 Runtime"
|
||||
VALUE "FileVersion", "10.0.17763.1 (WinBuild.160101.0800)"
|
||||
VALUE "InternalName", "D3D10_1.dll"
|
||||
VALUE "LegalCopyright", "zlib/libpng license"
|
||||
VALUE "OriginalFilename", "D3D10_1.dll"
|
||||
VALUE "ProductName", "DXVK"
|
||||
VALUE "ProductVersion", "10.0.17763.1"
|
||||
END
|
||||
END
|
||||
BLOCK "VarFileInfo"
|
||||
BEGIN
|
||||
VALUE "Translation", 0x0809, 1200
|
||||
END
|
||||
END
|
||||
|
10
src/d3d11/d3d11.sym
Normal file
10
src/d3d11/d3d11.sym
Normal file
@ -0,0 +1,10 @@
|
||||
{
|
||||
global:
|
||||
D3D11CoreCreateDevice;
|
||||
D3D11CreateDevice;
|
||||
D3D11CreateDeviceAndSwapChain;
|
||||
D3D11On12CreateDevice;
|
||||
|
||||
local:
|
||||
*;
|
||||
};
|
@ -1,8 +1,10 @@
|
||||
#include "d3d11_annotation.h"
|
||||
#include "d3d11_context.h"
|
||||
#include "d3d11_context_def.h"
|
||||
#include "d3d11_context_imm.h"
|
||||
#include "d3d11_device.h"
|
||||
|
||||
#include "../util/util_misc.h"
|
||||
#include "../util/util_win32_compat.h"
|
||||
|
||||
namespace dxvk {
|
||||
|
||||
@ -30,46 +32,50 @@ namespace dxvk {
|
||||
registrationFunction(annotation);
|
||||
}
|
||||
|
||||
D3D11UserDefinedAnnotation::D3D11UserDefinedAnnotation(D3D11DeviceContext* ctx)
|
||||
: m_container(ctx),
|
||||
m_eventDepth(0) {
|
||||
if (m_container->IsAnnotationEnabled())
|
||||
|
||||
template<typename ContextType>
|
||||
D3D11UserDefinedAnnotation<ContextType>::D3D11UserDefinedAnnotation(
|
||||
ContextType* container,
|
||||
const Rc<DxvkDevice>& dxvkDevice)
|
||||
: m_container(container), m_eventDepth(0),
|
||||
m_annotationsEnabled(dxvkDevice->instance()->extensions().extDebugUtils) {
|
||||
if (!IsDeferred && m_annotationsEnabled)
|
||||
RegisterUserDefinedAnnotation<true>(this);
|
||||
}
|
||||
|
||||
D3D11UserDefinedAnnotation::D3D11UserDefinedAnnotation(const D3D11UserDefinedAnnotation&)
|
||||
{
|
||||
if (m_container->IsAnnotationEnabled())
|
||||
RegisterUserDefinedAnnotation<true>(this);
|
||||
}
|
||||
|
||||
D3D11UserDefinedAnnotation::~D3D11UserDefinedAnnotation() {
|
||||
if (m_container->IsAnnotationEnabled())
|
||||
template<typename ContextType>
|
||||
D3D11UserDefinedAnnotation<ContextType>::~D3D11UserDefinedAnnotation() {
|
||||
if (!IsDeferred && m_annotationsEnabled)
|
||||
RegisterUserDefinedAnnotation<false>(this);
|
||||
}
|
||||
|
||||
|
||||
ULONG STDMETHODCALLTYPE D3D11UserDefinedAnnotation::AddRef() {
|
||||
template<typename ContextType>
|
||||
ULONG STDMETHODCALLTYPE D3D11UserDefinedAnnotation<ContextType>::AddRef() {
|
||||
return m_container->AddRef();
|
||||
}
|
||||
|
||||
|
||||
ULONG STDMETHODCALLTYPE D3D11UserDefinedAnnotation::Release() {
|
||||
template<typename ContextType>
|
||||
ULONG STDMETHODCALLTYPE D3D11UserDefinedAnnotation<ContextType>::Release() {
|
||||
return m_container->Release();
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D11UserDefinedAnnotation::QueryInterface(
|
||||
template<typename ContextType>
|
||||
HRESULT STDMETHODCALLTYPE D3D11UserDefinedAnnotation<ContextType>::QueryInterface(
|
||||
REFIID riid,
|
||||
void** ppvObject) {
|
||||
return m_container->QueryInterface(riid, ppvObject);
|
||||
}
|
||||
|
||||
|
||||
INT STDMETHODCALLTYPE D3D11UserDefinedAnnotation::BeginEvent(
|
||||
template<typename ContextType>
|
||||
INT STDMETHODCALLTYPE D3D11UserDefinedAnnotation<ContextType>::BeginEvent(
|
||||
D3DCOLOR Color,
|
||||
LPCWSTR Name) {
|
||||
if (!m_container->IsAnnotationEnabled())
|
||||
if (!m_annotationsEnabled)
|
||||
return -1;
|
||||
|
||||
D3D10DeviceLock lock = m_container->LockContext();
|
||||
@ -88,8 +94,9 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
INT STDMETHODCALLTYPE D3D11UserDefinedAnnotation::EndEvent() {
|
||||
if (!m_container->IsAnnotationEnabled())
|
||||
template<typename ContextType>
|
||||
INT STDMETHODCALLTYPE D3D11UserDefinedAnnotation<ContextType>::EndEvent() {
|
||||
if (!m_annotationsEnabled)
|
||||
return -1;
|
||||
|
||||
D3D10DeviceLock lock = m_container->LockContext();
|
||||
@ -102,10 +109,11 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11UserDefinedAnnotation::SetMarker(
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11UserDefinedAnnotation<ContextType>::SetMarker(
|
||||
D3DCOLOR Color,
|
||||
LPCWSTR Name) {
|
||||
if (!m_container->IsAnnotationEnabled())
|
||||
if (!m_annotationsEnabled)
|
||||
return;
|
||||
|
||||
D3D10DeviceLock lock = m_container->LockContext();
|
||||
@ -122,8 +130,13 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
BOOL STDMETHODCALLTYPE D3D11UserDefinedAnnotation::GetStatus() {
|
||||
return m_container->IsAnnotationEnabled();
|
||||
template<typename ContextType>
|
||||
BOOL STDMETHODCALLTYPE D3D11UserDefinedAnnotation<ContextType>::GetStatus() {
|
||||
return m_annotationsEnabled;
|
||||
}
|
||||
|
||||
|
||||
template class D3D11UserDefinedAnnotation<D3D11DeferredContext>;
|
||||
template class D3D11UserDefinedAnnotation<D3D11ImmediateContext>;
|
||||
|
||||
}
|
||||
|
@ -1,20 +1,31 @@
|
||||
#pragma once
|
||||
|
||||
#include <type_traits>
|
||||
|
||||
#include "d3d11_include.h"
|
||||
|
||||
#include "../dxvk/dxvk_annotation.h"
|
||||
#include "../dxvk/dxvk_device.h"
|
||||
|
||||
namespace dxvk {
|
||||
|
||||
class D3D11DeviceContext;
|
||||
class D3D11DeferredContext;
|
||||
class D3D11ImmediateContext;
|
||||
|
||||
template<typename ContextType>
|
||||
class D3D11UserDefinedAnnotation final : public IDXVKUserDefinedAnnotation {
|
||||
|
||||
constexpr static bool IsDeferred = std::is_same_v<ContextType, D3D11DeferredContext>;
|
||||
public:
|
||||
|
||||
D3D11UserDefinedAnnotation(D3D11DeviceContext* ctx);
|
||||
D3D11UserDefinedAnnotation(const D3D11UserDefinedAnnotation&);
|
||||
D3D11UserDefinedAnnotation(
|
||||
ContextType* container,
|
||||
const Rc<DxvkDevice>& dxvkDevice);
|
||||
|
||||
~D3D11UserDefinedAnnotation();
|
||||
|
||||
D3D11UserDefinedAnnotation (const D3D11UserDefinedAnnotation&) = delete;
|
||||
D3D11UserDefinedAnnotation& operator = (const D3D11UserDefinedAnnotation&) = delete;
|
||||
|
||||
ULONG STDMETHODCALLTYPE AddRef();
|
||||
|
||||
ULONG STDMETHODCALLTYPE Release();
|
||||
@ -37,10 +48,9 @@ namespace dxvk {
|
||||
|
||||
private:
|
||||
|
||||
D3D11DeviceContext* m_container;
|
||||
|
||||
// Stack depth for non-finalized BeginEvent calls
|
||||
int32_t m_eventDepth;
|
||||
ContextType* m_container;
|
||||
int32_t m_eventDepth;
|
||||
bool m_annotationsEnabled;
|
||||
};
|
||||
|
||||
}
|
||||
|
@ -58,8 +58,11 @@ namespace dxvk {
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
Logger::warn("D3D11BlendState::QueryInterface: Unknown interface query");
|
||||
Logger::warn(str::format(riid));
|
||||
if (logQueryInterfaceError(__uuidof(ID3D11BlendState), riid)) {
|
||||
Logger::warn("D3D11BlendState::QueryInterface: Unknown interface query");
|
||||
Logger::warn(str::format(riid));
|
||||
}
|
||||
|
||||
return E_NOINTERFACE;
|
||||
}
|
||||
|
||||
@ -87,7 +90,7 @@ namespace dxvk {
|
||||
|
||||
|
||||
void D3D11BlendState::BindToContext(
|
||||
const Rc<DxvkContext>& ctx,
|
||||
DxvkContext* ctx,
|
||||
uint32_t sampleMask) const {
|
||||
// We handled Independent Blend during object creation
|
||||
// already, so if it is disabled, all elements in the
|
||||
|
@ -33,7 +33,7 @@ namespace dxvk {
|
||||
D3D11_BLEND_DESC1* pDesc) final;
|
||||
|
||||
void BindToContext(
|
||||
const Rc<DxvkContext>& ctx,
|
||||
DxvkContext* ctx,
|
||||
UINT sampleMask) const;
|
||||
|
||||
D3D10BlendState* GetD3D10Iface() {
|
||||
|
@ -8,12 +8,14 @@ namespace dxvk {
|
||||
|
||||
D3D11Buffer::D3D11Buffer(
|
||||
D3D11Device* pDevice,
|
||||
const D3D11_BUFFER_DESC* pDesc)
|
||||
const D3D11_BUFFER_DESC* pDesc,
|
||||
const D3D11_ON_12_RESOURCE_INFO* p11on12Info)
|
||||
: D3D11DeviceChild<ID3D11Buffer>(pDevice),
|
||||
m_desc (*pDesc),
|
||||
m_resource (this),
|
||||
m_d3d10 (this) {
|
||||
DxvkBufferCreateInfo info;
|
||||
DxvkBufferCreateInfo info;
|
||||
info.flags = 0;
|
||||
info.size = pDesc->ByteWidth;
|
||||
info.usage = VK_BUFFER_USAGE_TRANSFER_SRC_BIT
|
||||
| VK_BUFFER_USAGE_TRANSFER_DST_BIT;
|
||||
@ -37,9 +39,6 @@ namespace dxvk {
|
||||
info.usage |= VK_BUFFER_USAGE_UNIFORM_BUFFER_BIT;
|
||||
info.stages |= m_parent->GetEnabledShaderStages();
|
||||
info.access |= VK_ACCESS_UNIFORM_READ_BIT;
|
||||
|
||||
if (m_parent->GetOptions()->constantBufferRangeCheck)
|
||||
info.usage |= VK_BUFFER_USAGE_STORAGE_BUFFER_BIT;
|
||||
}
|
||||
|
||||
if (pDesc->BindFlags & D3D11_BIND_SHADER_RESOURCE) {
|
||||
@ -69,12 +68,50 @@ namespace dxvk {
|
||||
info.access |= VK_ACCESS_INDIRECT_COMMAND_READ_BIT;
|
||||
}
|
||||
|
||||
// Create the buffer and set the entire buffer slice as mapped,
|
||||
// so that we only have to update it when invalidating th buffer
|
||||
m_buffer = m_parent->GetDXVKDevice()->createBuffer(info, GetMemoryFlags());
|
||||
m_mapped = m_buffer->getSliceHandle();
|
||||
if (pDesc->MiscFlags & D3D11_RESOURCE_MISC_TILED) {
|
||||
info.flags |= VK_BUFFER_CREATE_SPARSE_BINDING_BIT
|
||||
| VK_BUFFER_CREATE_SPARSE_RESIDENCY_BIT
|
||||
| VK_BUFFER_CREATE_SPARSE_ALIASED_BIT;
|
||||
}
|
||||
|
||||
m_mapMode = DetermineMapMode();
|
||||
// Set host read bit as necessary. We may internally read staging
|
||||
// buffer contents even if the buffer is not marked for reading.
|
||||
if (pDesc->CPUAccessFlags && pDesc->Usage != D3D11_USAGE_DYNAMIC) {
|
||||
info.stages |= VK_PIPELINE_STAGE_HOST_BIT;
|
||||
info.access |= VK_ACCESS_HOST_READ_BIT;
|
||||
|
||||
if (pDesc->CPUAccessFlags & D3D11_CPU_ACCESS_WRITE)
|
||||
info.access |= VK_ACCESS_HOST_WRITE_BIT;
|
||||
}
|
||||
|
||||
if (p11on12Info) {
|
||||
m_11on12 = *p11on12Info;
|
||||
|
||||
DxvkBufferImportInfo importInfo;
|
||||
importInfo.buffer = VkBuffer(m_11on12.VulkanHandle);
|
||||
importInfo.offset = m_11on12.VulkanOffset;
|
||||
|
||||
if (m_desc.CPUAccessFlags)
|
||||
m_11on12.Resource->Map(0, nullptr, &importInfo.mapPtr);
|
||||
|
||||
m_buffer = m_parent->GetDXVKDevice()->importBuffer(info, importInfo, GetMemoryFlags());
|
||||
m_mapped = m_buffer->getSliceHandle();
|
||||
|
||||
m_mapMode = DetermineMapMode();
|
||||
} else if (!(pDesc->MiscFlags & D3D11_RESOURCE_MISC_TILE_POOL)) {
|
||||
// Create the buffer and set the entire buffer slice as mapped,
|
||||
// so that we only have to update it when invalidating the buffer
|
||||
m_buffer = m_parent->GetDXVKDevice()->createBuffer(info, GetMemoryFlags());
|
||||
m_mapped = m_buffer->getSliceHandle();
|
||||
|
||||
m_mapMode = DetermineMapMode();
|
||||
} else {
|
||||
m_sparseAllocator = m_parent->GetDXVKDevice()->createSparsePageAllocator();
|
||||
m_sparseAllocator->setCapacity(info.size / SparseMemoryPageSize);
|
||||
|
||||
m_mapped = DxvkBufferSliceHandle();
|
||||
m_mapMode = D3D11_COMMON_BUFFER_MAP_MODE_NONE;
|
||||
}
|
||||
|
||||
// For Stream Output buffers we need a counter
|
||||
if (pDesc->BindFlags & D3D11_BIND_STREAM_OUTPUT)
|
||||
@ -83,7 +120,8 @@ namespace dxvk {
|
||||
|
||||
|
||||
D3D11Buffer::~D3D11Buffer() {
|
||||
|
||||
if (m_desc.CPUAccessFlags && m_11on12.Resource != nullptr)
|
||||
m_11on12.Resource->Unmap(0, nullptr);
|
||||
}
|
||||
|
||||
|
||||
@ -116,8 +154,11 @@ namespace dxvk {
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
Logger::warn("D3D11Buffer::QueryInterface: Unknown interface query");
|
||||
Logger::warn(str::format(riid));
|
||||
if (logQueryInterfaceError(__uuidof(ID3D11Buffer), riid)) {
|
||||
Logger::warn("D3D11Buffer::QueryInterface: Unknown interface query");
|
||||
Logger::warn(str::format(riid));
|
||||
}
|
||||
|
||||
return E_NOINTERFACE;
|
||||
}
|
||||
|
||||
@ -159,7 +200,7 @@ namespace dxvk {
|
||||
// Check whether the given combination of buffer view
|
||||
// type and view format is supported by the device
|
||||
DXGI_VK_FORMAT_INFO viewFormat = m_parent->LookupFormat(Format, DXGI_VK_FORMAT_MODE_ANY);
|
||||
VkFormatFeatureFlags features = GetBufferFormatFeatures(BindFlags);
|
||||
VkFormatFeatureFlags2 features = GetBufferFormatFeatures(BindFlags);
|
||||
|
||||
return CheckFormatFeatureSupport(viewFormat.Format, features);
|
||||
}
|
||||
@ -167,13 +208,9 @@ namespace dxvk {
|
||||
|
||||
HRESULT D3D11Buffer::NormalizeBufferProperties(D3D11_BUFFER_DESC* pDesc) {
|
||||
// Zero-sized buffers are illegal
|
||||
if (!pDesc->ByteWidth)
|
||||
if (!pDesc->ByteWidth && !(pDesc->MiscFlags & D3D11_RESOURCE_MISC_TILE_POOL))
|
||||
return E_INVALIDARG;
|
||||
|
||||
// We don't support tiled resources
|
||||
if (pDesc->MiscFlags & (D3D11_RESOURCE_MISC_TILE_POOL | D3D11_RESOURCE_MISC_TILED))
|
||||
return E_INVALIDARG;
|
||||
|
||||
// Constant buffer size must be a multiple of 16
|
||||
if ((pDesc->BindFlags & D3D11_BIND_CONSTANT_BUFFER)
|
||||
&& (pDesc->ByteWidth & 0xF))
|
||||
@ -194,7 +231,25 @@ namespace dxvk {
|
||||
// Mip generation obviously doesn't work for buffers
|
||||
if (pDesc->MiscFlags & D3D11_RESOURCE_MISC_GENERATE_MIPS)
|
||||
return E_INVALIDARG;
|
||||
|
||||
|
||||
// Basic validation for tiled buffers
|
||||
if (pDesc->MiscFlags & D3D11_RESOURCE_MISC_TILED) {
|
||||
if ((pDesc->MiscFlags & D3D11_RESOURCE_MISC_TILE_POOL)
|
||||
|| (pDesc->Usage != D3D11_USAGE_DEFAULT)
|
||||
|| (pDesc->CPUAccessFlags))
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
|
||||
// Basic validation for tile pools
|
||||
if (pDesc->MiscFlags & D3D11_RESOURCE_MISC_TILE_POOL) {
|
||||
if ((pDesc->MiscFlags & ~D3D11_RESOURCE_MISC_TILE_POOL)
|
||||
|| (pDesc->ByteWidth % SparseMemoryPageSize)
|
||||
|| (pDesc->Usage != D3D11_USAGE_DEFAULT)
|
||||
|| (pDesc->BindFlags)
|
||||
|| (pDesc->CPUAccessFlags))
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
|
||||
if (!(pDesc->MiscFlags & D3D11_RESOURCE_MISC_BUFFER_STRUCTURED))
|
||||
pDesc->StructureByteStride = 0;
|
||||
|
||||
@ -202,17 +257,50 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
HRESULT D3D11Buffer::GetDescFromD3D12(
|
||||
ID3D12Resource* pResource,
|
||||
const D3D11_RESOURCE_FLAGS* pResourceFlags,
|
||||
D3D11_BUFFER_DESC* pBufferDesc) {
|
||||
D3D12_RESOURCE_DESC desc12 = pResource->GetDesc();
|
||||
|
||||
pBufferDesc->ByteWidth = desc12.Width;
|
||||
pBufferDesc->Usage = D3D11_USAGE_DEFAULT;
|
||||
pBufferDesc->BindFlags = D3D11_BIND_SHADER_RESOURCE;
|
||||
pBufferDesc->MiscFlags = 0;
|
||||
pBufferDesc->CPUAccessFlags = 0;
|
||||
pBufferDesc->StructureByteStride = 0;
|
||||
|
||||
if (desc12.Flags & D3D12_RESOURCE_FLAG_ALLOW_RENDER_TARGET)
|
||||
pBufferDesc->BindFlags |= D3D11_BIND_RENDER_TARGET;
|
||||
|
||||
if (desc12.Flags & D3D12_RESOURCE_FLAG_ALLOW_UNORDERED_ACCESS)
|
||||
pBufferDesc->BindFlags |= D3D11_BIND_UNORDERED_ACCESS;
|
||||
|
||||
if (pResourceFlags) {
|
||||
pBufferDesc->BindFlags = pResourceFlags->BindFlags;
|
||||
pBufferDesc->MiscFlags |= pResourceFlags->MiscFlags;
|
||||
pBufferDesc->CPUAccessFlags = pResourceFlags->CPUAccessFlags;
|
||||
pBufferDesc->StructureByteStride = pResourceFlags->StructureByteStride;
|
||||
}
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
BOOL D3D11Buffer::CheckFormatFeatureSupport(
|
||||
VkFormat Format,
|
||||
VkFormatFeatureFlags Features) const {
|
||||
VkFormatProperties properties = m_parent->GetDXVKDevice()->adapter()->formatProperties(Format);
|
||||
return (properties.bufferFeatures & Features) == Features;
|
||||
VkFormatFeatureFlags2 Features) const {
|
||||
DxvkFormatFeatures support = m_parent->GetDXVKDevice()->getFormatFeatures(Format);
|
||||
return (support.buffer & Features) == Features;
|
||||
}
|
||||
|
||||
|
||||
VkMemoryPropertyFlags D3D11Buffer::GetMemoryFlags() const {
|
||||
VkMemoryPropertyFlags memoryFlags = 0;
|
||||
|
||||
|
||||
if (m_desc.MiscFlags & (D3D11_RESOURCE_MISC_TILE_POOL | D3D11_RESOURCE_MISC_TILED))
|
||||
return VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT;
|
||||
|
||||
switch (m_desc.Usage) {
|
||||
case D3D11_USAGE_IMMUTABLE:
|
||||
memoryFlags |= VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT;
|
||||
@ -251,6 +339,7 @@ namespace dxvk {
|
||||
|| (m_parent->GetOptions()->cachedDynamicResources & m_desc.BindFlags);
|
||||
|
||||
if ((memoryFlags & VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT) && useCached) {
|
||||
memoryFlags &= ~VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT;
|
||||
memoryFlags |= VK_MEMORY_PROPERTY_HOST_COHERENT_BIT
|
||||
| VK_MEMORY_PROPERTY_HOST_CACHED_BIT;
|
||||
}
|
||||
|
@ -7,12 +7,12 @@
|
||||
|
||||
#include "d3d11_device_child.h"
|
||||
#include "d3d11_interfaces.h"
|
||||
#include "d3d11_on_12.h"
|
||||
#include "d3d11_resource.h"
|
||||
|
||||
namespace dxvk {
|
||||
|
||||
class D3D11Device;
|
||||
class D3D11DeviceContext;
|
||||
|
||||
|
||||
/**
|
||||
@ -42,7 +42,9 @@ namespace dxvk {
|
||||
|
||||
D3D11Buffer(
|
||||
D3D11Device* pDevice,
|
||||
const D3D11_BUFFER_DESC* pDesc);
|
||||
const D3D11_BUFFER_DESC* pDesc,
|
||||
const D3D11_ON_12_RESOURCE_INFO* p11on12Info);
|
||||
|
||||
~D3D11Buffer();
|
||||
|
||||
HRESULT STDMETHODCALLTYPE QueryInterface(
|
||||
@ -67,6 +69,10 @@ namespace dxvk {
|
||||
return &m_desc;
|
||||
}
|
||||
|
||||
BOOL IsTilePool() const {
|
||||
return bool(m_desc.MiscFlags & D3D11_RESOURCE_MISC_TILE_POOL);
|
||||
}
|
||||
|
||||
D3D11_COMMON_BUFFER_MAP_MODE GetMapMode() const {
|
||||
return m_mapMode;
|
||||
}
|
||||
@ -74,6 +80,10 @@ namespace dxvk {
|
||||
Rc<DxvkBuffer> GetBuffer() const {
|
||||
return m_buffer;
|
||||
}
|
||||
|
||||
Rc<DxvkSparsePageAllocator> GetSparseAllocator() const {
|
||||
return m_sparseAllocator;
|
||||
}
|
||||
|
||||
DxvkBufferSlice GetBufferSlice() const {
|
||||
return DxvkBufferSlice(m_buffer, 0, m_desc.ByteWidth);
|
||||
@ -81,18 +91,20 @@ namespace dxvk {
|
||||
|
||||
DxvkBufferSlice GetBufferSlice(VkDeviceSize offset) const {
|
||||
VkDeviceSize size = m_desc.ByteWidth;
|
||||
|
||||
return likely(offset < size)
|
||||
? DxvkBufferSlice(m_buffer, offset, size - offset)
|
||||
: DxvkBufferSlice();
|
||||
offset = std::min(offset, size);
|
||||
return DxvkBufferSlice(m_buffer, offset, size - offset);
|
||||
}
|
||||
|
||||
DxvkBufferSlice GetBufferSlice(VkDeviceSize offset, VkDeviceSize length) const {
|
||||
VkDeviceSize size = m_desc.ByteWidth;
|
||||
offset = std::min(offset, size);
|
||||
return DxvkBufferSlice(m_buffer, offset, std::min(length, size - offset));
|
||||
}
|
||||
|
||||
return likely(offset < size)
|
||||
? DxvkBufferSlice(m_buffer, offset, std::min(length, size - offset))
|
||||
: DxvkBufferSlice();
|
||||
VkDeviceSize GetRemainingSize(VkDeviceSize offset) const {
|
||||
VkDeviceSize size = m_desc.ByteWidth;
|
||||
offset = std::min(offset, size);
|
||||
return size - offset;
|
||||
}
|
||||
|
||||
DxvkBufferSlice GetSOCounter() {
|
||||
@ -133,6 +145,14 @@ namespace dxvk {
|
||||
: DxvkCsThread::SynchronizeAll;
|
||||
}
|
||||
|
||||
/**
|
||||
* \brief Retrieves D3D11on12 resource info
|
||||
* \returns 11on12 resource info
|
||||
*/
|
||||
D3D11_ON_12_RESOURCE_INFO Get11on12Info() const {
|
||||
return m_11on12;
|
||||
}
|
||||
|
||||
/**
|
||||
* \brief Normalizes buffer description
|
||||
*
|
||||
@ -142,13 +162,28 @@ namespace dxvk {
|
||||
static HRESULT NormalizeBufferProperties(
|
||||
D3D11_BUFFER_DESC* pDesc);
|
||||
|
||||
/**
|
||||
* \brief Initializes D3D11 buffer description from D3D12
|
||||
*
|
||||
* \param [in] pResource D3D12 resource
|
||||
* \param [in] pResourceFlags D3D11 flag overrides
|
||||
* \param [out] pBufferDesc D3D11 buffer description
|
||||
* \returns \c S_OK if the parameters are valid
|
||||
*/
|
||||
static HRESULT GetDescFromD3D12(
|
||||
ID3D12Resource* pResource,
|
||||
const D3D11_RESOURCE_FLAGS* pResourceFlags,
|
||||
D3D11_BUFFER_DESC* pBufferDesc);
|
||||
|
||||
private:
|
||||
|
||||
D3D11_BUFFER_DESC m_desc;
|
||||
D3D11_ON_12_RESOURCE_INFO m_11on12;
|
||||
D3D11_COMMON_BUFFER_MAP_MODE m_mapMode;
|
||||
|
||||
Rc<DxvkBuffer> m_buffer;
|
||||
Rc<DxvkBuffer> m_soCounter;
|
||||
Rc<DxvkSparsePageAllocator> m_sparseAllocator;
|
||||
DxvkBufferSliceHandle m_mapped;
|
||||
uint64_t m_seq = 0ull;
|
||||
|
||||
@ -157,7 +192,7 @@ namespace dxvk {
|
||||
|
||||
BOOL CheckFormatFeatureSupport(
|
||||
VkFormat Format,
|
||||
VkFormatFeatureFlags Features) const;
|
||||
VkFormatFeatureFlags2 Features) const;
|
||||
|
||||
VkMemoryPropertyFlags GetMemoryFlags() const;
|
||||
|
||||
|
@ -28,8 +28,11 @@ namespace dxvk {
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
Logger::warn("D3D11ClassLinkage::QueryInterface: Unknown interface query");
|
||||
Logger::warn(str::format(riid));
|
||||
if (logQueryInterfaceError(__uuidof(ID3D11ClassLinkage), riid)) {
|
||||
Logger::warn("D3D11ClassLinkage::QueryInterface: Unknown interface query");
|
||||
Logger::warn(str::format(riid));
|
||||
}
|
||||
|
||||
return E_NOINTERFACE;
|
||||
}
|
||||
|
||||
|
@ -30,8 +30,11 @@ namespace dxvk {
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
Logger::warn("D3D11CommandList::QueryInterface: Unknown interface query");
|
||||
Logger::warn(str::format(riid));
|
||||
if (logQueryInterfaceError(__uuidof(ID3D11CommandList), riid)) {
|
||||
Logger::warn("D3D11CommandList::QueryInterface: Unknown interface query");
|
||||
Logger::warn(str::format(riid));
|
||||
}
|
||||
|
||||
return E_NOINTERFACE;
|
||||
}
|
||||
|
||||
@ -41,54 +44,79 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
void D3D11CommandList::AddChunk(DxvkCsChunkRef&& Chunk) {
|
||||
m_chunks.push_back(std::move(Chunk));
|
||||
}
|
||||
|
||||
|
||||
void D3D11CommandList::AddQuery(D3D11Query* pQuery) {
|
||||
m_queries.emplace_back(pQuery);
|
||||
}
|
||||
|
||||
|
||||
void D3D11CommandList::EmitToCommandList(ID3D11CommandList* pCommandList) {
|
||||
auto cmdList = static_cast<D3D11CommandList*>(pCommandList);
|
||||
|
||||
for (const auto& chunk : m_chunks)
|
||||
cmdList->m_chunks.push_back(chunk);
|
||||
|
||||
for (const auto& query : m_queries)
|
||||
cmdList->m_queries.push_back(query);
|
||||
|
||||
for (const auto& resource : m_resources)
|
||||
cmdList->m_resources.push_back(resource);
|
||||
|
||||
MarkSubmitted();
|
||||
uint64_t D3D11CommandList::AddChunk(DxvkCsChunkRef&& Chunk) {
|
||||
m_chunks.push_back(std::move(Chunk));
|
||||
return m_chunks.size() - 1;
|
||||
}
|
||||
|
||||
|
||||
uint64_t D3D11CommandList::EmitToCsThread(DxvkCsThread* CsThread) {
|
||||
uint64_t seq = 0;
|
||||
uint64_t D3D11CommandList::AddCommandList(
|
||||
D3D11CommandList* pCommandList) {
|
||||
// This will be the chunk ID of the first chunk
|
||||
// added, for the purpose of resource tracking.
|
||||
uint64_t baseChunkId = m_chunks.size();
|
||||
|
||||
for (const auto& chunk : pCommandList->m_chunks)
|
||||
m_chunks.push_back(chunk);
|
||||
|
||||
for (const auto& query : pCommandList->m_queries)
|
||||
m_queries.push_back(query);
|
||||
|
||||
for (const auto& resource : pCommandList->m_resources) {
|
||||
TrackedResource entry = resource;
|
||||
entry.chunkId += baseChunkId;
|
||||
|
||||
m_resources.push_back(std::move(entry));
|
||||
}
|
||||
|
||||
pCommandList->MarkSubmitted();
|
||||
|
||||
// Return ID of the last chunk added. The command list
|
||||
// added can never be empty, so do not handle zero.
|
||||
return m_chunks.size() - 1;
|
||||
}
|
||||
|
||||
|
||||
void D3D11CommandList::EmitToCsThread(
|
||||
const D3D11ChunkDispatchProc& DispatchProc) {
|
||||
for (const auto& query : m_queries)
|
||||
query->DoDeferredEnd();
|
||||
|
||||
for (const auto& chunk : m_chunks)
|
||||
seq = CsThread->dispatchChunk(DxvkCsChunkRef(chunk));
|
||||
|
||||
for (const auto& resource : m_resources)
|
||||
TrackResourceSequenceNumber(resource, seq);
|
||||
for (size_t i = 0, j = 0; i < m_chunks.size(); i++) {
|
||||
// If there are resources to track for the current chunk,
|
||||
// use a strong flush hint to dispatch GPU work quickly.
|
||||
GpuFlushType flushType = GpuFlushType::ImplicitWeakHint;
|
||||
|
||||
if (j < m_resources.size() && m_resources[j].chunkId == i)
|
||||
flushType = GpuFlushType::ImplicitStrongHint;
|
||||
|
||||
// Dispatch the chunk and capture its sequence number
|
||||
uint64_t seq = DispatchProc(DxvkCsChunkRef(m_chunks[i]), flushType);
|
||||
|
||||
// Track resource sequence numbers for the added chunk
|
||||
while (j < m_resources.size() && m_resources[j].chunkId == i)
|
||||
TrackResourceSequenceNumber(m_resources[j++].ref, seq);
|
||||
}
|
||||
|
||||
MarkSubmitted();
|
||||
return seq;
|
||||
}
|
||||
|
||||
|
||||
void D3D11CommandList::TrackResourceUsage(
|
||||
ID3D11Resource* pResource,
|
||||
D3D11_RESOURCE_DIMENSION ResourceType,
|
||||
UINT Subresource) {
|
||||
m_resources.emplace_back(pResource, Subresource, ResourceType);
|
||||
UINT Subresource,
|
||||
uint64_t ChunkId) {
|
||||
TrackedResource entry;
|
||||
entry.ref = D3D11ResourceRef(pResource, Subresource, ResourceType);
|
||||
entry.chunkId = ChunkId;
|
||||
|
||||
m_resources.push_back(std::move(entry));
|
||||
}
|
||||
|
||||
|
||||
@ -96,7 +124,6 @@ namespace dxvk {
|
||||
const D3D11ResourceRef& Resource,
|
||||
uint64_t Seq) {
|
||||
ID3D11Resource* iface = Resource.Get();
|
||||
UINT subresource = Resource.GetSubresource();
|
||||
|
||||
switch (Resource.GetType()) {
|
||||
case D3D11_RESOURCE_DIMENSION_UNKNOWN:
|
||||
@ -109,17 +136,17 @@ namespace dxvk {
|
||||
|
||||
case D3D11_RESOURCE_DIMENSION_TEXTURE1D: {
|
||||
auto impl = static_cast<D3D11Texture1D*>(iface)->GetCommonTexture();
|
||||
impl->TrackSequenceNumber(subresource, Seq);
|
||||
impl->TrackSequenceNumber(Resource.GetSubresource(), Seq);
|
||||
} break;
|
||||
|
||||
case D3D11_RESOURCE_DIMENSION_TEXTURE2D: {
|
||||
auto impl = static_cast<D3D11Texture2D*>(iface)->GetCommonTexture();
|
||||
impl->TrackSequenceNumber(subresource, Seq);
|
||||
impl->TrackSequenceNumber(Resource.GetSubresource(), Seq);
|
||||
} break;
|
||||
|
||||
case D3D11_RESOURCE_DIMENSION_TEXTURE3D: {
|
||||
auto impl = static_cast<D3D11Texture3D*>(iface)->GetCommonTexture();
|
||||
impl->TrackSequenceNumber(subresource, Seq);
|
||||
impl->TrackSequenceNumber(Resource.GetSubresource(), Seq);
|
||||
} break;
|
||||
}
|
||||
}
|
||||
|
@ -1,9 +1,13 @@
|
||||
#pragma once
|
||||
|
||||
#include <functional>
|
||||
|
||||
#include "d3d11_context.h"
|
||||
|
||||
namespace dxvk {
|
||||
|
||||
using D3D11ChunkDispatchProc = std::function<uint64_t (DxvkCsChunkRef&&, GpuFlushType)>;
|
||||
|
||||
class D3D11CommandList : public D3D11DeviceChild<ID3D11CommandList> {
|
||||
|
||||
public:
|
||||
@ -20,30 +24,36 @@ namespace dxvk {
|
||||
|
||||
UINT STDMETHODCALLTYPE GetContextFlags() final;
|
||||
|
||||
void AddChunk(
|
||||
DxvkCsChunkRef&& Chunk);
|
||||
|
||||
void AddQuery(
|
||||
D3D11Query* pQuery);
|
||||
|
||||
void EmitToCommandList(
|
||||
ID3D11CommandList* pCommandList);
|
||||
|
||||
uint64_t EmitToCsThread(
|
||||
DxvkCsThread* CsThread);
|
||||
uint64_t AddChunk(
|
||||
DxvkCsChunkRef&& Chunk);
|
||||
|
||||
uint64_t AddCommandList(
|
||||
D3D11CommandList* pCommandList);
|
||||
|
||||
void EmitToCsThread(
|
||||
const D3D11ChunkDispatchProc& DispatchProc);
|
||||
|
||||
void TrackResourceUsage(
|
||||
ID3D11Resource* pResource,
|
||||
D3D11_RESOURCE_DIMENSION ResourceType,
|
||||
UINT Subresource);
|
||||
UINT Subresource,
|
||||
uint64_t ChunkId);
|
||||
|
||||
private:
|
||||
|
||||
UINT const m_contextFlags;
|
||||
struct TrackedResource {
|
||||
D3D11ResourceRef ref;
|
||||
uint64_t chunkId;
|
||||
};
|
||||
|
||||
UINT m_contextFlags;
|
||||
|
||||
std::vector<DxvkCsChunkRef> m_chunks;
|
||||
std::vector<Com<D3D11Query, false>> m_queries;
|
||||
std::vector<D3D11ResourceRef> m_resources;
|
||||
std::vector<TrackedResource> m_resources;
|
||||
|
||||
std::atomic<bool> m_submitted = { false };
|
||||
std::atomic<bool> m_warned = { false };
|
||||
|
@ -1,43 +1,43 @@
|
||||
#include <cstring>
|
||||
#include <algorithm>
|
||||
|
||||
#include "d3d11_context.h"
|
||||
#include "d3d11_device.h"
|
||||
#include "d3d11_query.h"
|
||||
#include "d3d11_texture.h"
|
||||
#include "d3d11_video.h"
|
||||
|
||||
#include "../dxbc/dxbc_util.h"
|
||||
#include "d3d11_context_def.h"
|
||||
#include "d3d11_context_imm.h"
|
||||
|
||||
namespace dxvk {
|
||||
|
||||
D3D11DeviceContext::D3D11DeviceContext(
|
||||
|
||||
template<typename ContextType>
|
||||
D3D11CommonContext<ContextType>::D3D11CommonContext(
|
||||
D3D11Device* pParent,
|
||||
const Rc<DxvkDevice>& Device,
|
||||
UINT ContextFlags,
|
||||
DxvkCsChunkFlags CsFlags)
|
||||
: D3D11DeviceChild<ID3D11DeviceContext4>(pParent),
|
||||
m_contextExt(this),
|
||||
m_multithread(this, false),
|
||||
m_contextExt(GetTypedContext()),
|
||||
m_annotation(GetTypedContext(), Device),
|
||||
m_device (Device),
|
||||
m_flags (ContextFlags),
|
||||
m_staging (Device, StagingBufferSize),
|
||||
m_annotation(this),
|
||||
m_csFlags (CsFlags),
|
||||
m_csChunk (AllocCsChunk()),
|
||||
m_cmdData (nullptr) {
|
||||
|
||||
}
|
||||
|
||||
|
||||
D3D11DeviceContext::~D3D11DeviceContext() {
|
||||
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
D3D11CommonContext<ContextType>::~D3D11CommonContext() {
|
||||
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D11DeviceContext::QueryInterface(REFIID riid, void** ppvObject) {
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
HRESULT STDMETHODCALLTYPE D3D11CommonContext<ContextType>::QueryInterface(REFIID riid, void** ppvObject) {
|
||||
if (ppvObject == nullptr)
|
||||
return E_POINTER;
|
||||
|
||||
*ppvObject = nullptr;
|
||||
|
||||
|
||||
if (riid == __uuidof(IUnknown)
|
||||
|| riid == __uuidof(ID3D11DeviceChild)
|
||||
|| riid == __uuidof(ID3D11DeviceContext)
|
||||
@ -48,36 +48,58 @@ namespace dxvk {
|
||||
*ppvObject = ref(this);
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
if (riid == __uuidof(ID3D11VkExtContext)
|
||||
|| riid == __uuidof(ID3D11VkExtContext1)) {
|
||||
*ppvObject = ref(&m_contextExt);
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
if (riid == __uuidof(ID3DUserDefinedAnnotation)
|
||||
|| riid == __uuidof(IDXVKUserDefinedAnnotation)) {
|
||||
*ppvObject = ref(&m_annotation);
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
if (riid == __uuidof(ID3D10Multithread)) {
|
||||
*ppvObject = ref(&m_multithread);
|
||||
return S_OK;
|
||||
if (logQueryInterfaceError(__uuidof(ID3D11DeviceContext), riid)) {
|
||||
Logger::warn("D3D11DeviceContext::QueryInterface: Unknown interface query");
|
||||
Logger::warn(str::format(riid));
|
||||
}
|
||||
|
||||
Logger::warn("D3D11DeviceContext::QueryInterface: Unknown interface query");
|
||||
Logger::warn(str::format(riid));
|
||||
|
||||
return E_NOINTERFACE;
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::DiscardResource(ID3D11Resource* pResource) {
|
||||
|
||||
template<typename ContextType>
|
||||
D3D11_DEVICE_CONTEXT_TYPE STDMETHODCALLTYPE D3D11CommonContext<ContextType>::GetType() {
|
||||
return IsDeferred
|
||||
? D3D11_DEVICE_CONTEXT_DEFERRED
|
||||
: D3D11_DEVICE_CONTEXT_IMMEDIATE;
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
UINT STDMETHODCALLTYPE D3D11CommonContext<ContextType>::GetContextFlags() {
|
||||
return m_flags;
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::ClearState() {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
ResetCommandListState();
|
||||
ResetContextState();
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::DiscardResource(ID3D11Resource* pResource) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
if (!pResource)
|
||||
return;
|
||||
|
||||
|
||||
// We don't support the Discard API for images
|
||||
D3D11_RESOURCE_DIMENSION resType = D3D11_RESOURCE_DIMENSION_UNKNOWN;
|
||||
pResource->GetType(&resType);
|
||||
@ -93,12 +115,14 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::DiscardView(ID3D11View* pResourceView) {
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::DiscardView(ID3D11View* pResourceView) {
|
||||
DiscardView1(pResourceView, nullptr, 0);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::DiscardView1(
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::DiscardView1(
|
||||
ID3D11View* pResourceView,
|
||||
const D3D11_RECT* pRects,
|
||||
UINT NumRects) {
|
||||
@ -144,153 +168,10 @@ namespace dxvk {
|
||||
ctx->discardImageView(cView, cView->formatInfo()->aspectMask);
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::ClearState() {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
// Default shaders
|
||||
m_state.vs.shader = nullptr;
|
||||
m_state.hs.shader = nullptr;
|
||||
m_state.ds.shader = nullptr;
|
||||
m_state.gs.shader = nullptr;
|
||||
m_state.ps.shader = nullptr;
|
||||
m_state.cs.shader = nullptr;
|
||||
|
||||
// Default constant buffers
|
||||
for (uint32_t i = 0; i < D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT; i++) {
|
||||
m_state.vs.constantBuffers[i] = { nullptr, 0, 0 };
|
||||
m_state.hs.constantBuffers[i] = { nullptr, 0, 0 };
|
||||
m_state.ds.constantBuffers[i] = { nullptr, 0, 0 };
|
||||
m_state.gs.constantBuffers[i] = { nullptr, 0, 0 };
|
||||
m_state.ps.constantBuffers[i] = { nullptr, 0, 0 };
|
||||
m_state.cs.constantBuffers[i] = { nullptr, 0, 0 };
|
||||
}
|
||||
|
||||
// Default samplers
|
||||
for (uint32_t i = 0; i < D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT; i++) {
|
||||
m_state.vs.samplers[i] = nullptr;
|
||||
m_state.hs.samplers[i] = nullptr;
|
||||
m_state.ds.samplers[i] = nullptr;
|
||||
m_state.gs.samplers[i] = nullptr;
|
||||
m_state.ps.samplers[i] = nullptr;
|
||||
m_state.cs.samplers[i] = nullptr;
|
||||
}
|
||||
|
||||
// Default shader resources
|
||||
for (uint32_t i = 0; i < D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT; i++) {
|
||||
m_state.vs.shaderResources.views[i] = nullptr;
|
||||
m_state.hs.shaderResources.views[i] = nullptr;
|
||||
m_state.ds.shaderResources.views[i] = nullptr;
|
||||
m_state.gs.shaderResources.views[i] = nullptr;
|
||||
m_state.ps.shaderResources.views[i] = nullptr;
|
||||
m_state.cs.shaderResources.views[i] = nullptr;
|
||||
}
|
||||
|
||||
m_state.vs.shaderResources.hazardous.clear();
|
||||
m_state.hs.shaderResources.hazardous.clear();
|
||||
m_state.ds.shaderResources.hazardous.clear();
|
||||
m_state.gs.shaderResources.hazardous.clear();
|
||||
m_state.ps.shaderResources.hazardous.clear();
|
||||
m_state.cs.shaderResources.hazardous.clear();
|
||||
|
||||
// Default UAVs
|
||||
for (uint32_t i = 0; i < D3D11_1_UAV_SLOT_COUNT; i++) {
|
||||
m_state.ps.unorderedAccessViews[i] = nullptr;
|
||||
m_state.cs.unorderedAccessViews[i] = nullptr;
|
||||
}
|
||||
|
||||
m_state.cs.uavMask.clear();
|
||||
|
||||
// Default ID state
|
||||
m_state.id.argBuffer = nullptr;
|
||||
|
||||
// Default IA state
|
||||
m_state.ia.inputLayout = nullptr;
|
||||
m_state.ia.primitiveTopology = D3D11_PRIMITIVE_TOPOLOGY_UNDEFINED;
|
||||
|
||||
for (uint32_t i = 0; i < D3D11_IA_VERTEX_INPUT_RESOURCE_SLOT_COUNT; i++) {
|
||||
m_state.ia.vertexBuffers[i].buffer = nullptr;
|
||||
m_state.ia.vertexBuffers[i].offset = 0;
|
||||
m_state.ia.vertexBuffers[i].stride = 0;
|
||||
}
|
||||
|
||||
m_state.ia.indexBuffer.buffer = nullptr;
|
||||
m_state.ia.indexBuffer.offset = 0;
|
||||
m_state.ia.indexBuffer.format = DXGI_FORMAT_UNKNOWN;
|
||||
|
||||
// Default OM State
|
||||
for (uint32_t i = 0; i < D3D11_SIMULTANEOUS_RENDER_TARGET_COUNT; i++)
|
||||
m_state.om.renderTargetViews[i] = nullptr;
|
||||
m_state.om.depthStencilView = nullptr;
|
||||
|
||||
m_state.om.cbState = nullptr;
|
||||
m_state.om.dsState = nullptr;
|
||||
|
||||
for (uint32_t i = 0; i < 4; i++)
|
||||
m_state.om.blendFactor[i] = 1.0f;
|
||||
|
||||
m_state.om.sampleMask = D3D11_DEFAULT_SAMPLE_MASK;
|
||||
m_state.om.stencilRef = D3D11_DEFAULT_STENCIL_REFERENCE;
|
||||
|
||||
m_state.om.maxRtv = 0;
|
||||
m_state.om.maxUav = 0;
|
||||
|
||||
// Default RS state
|
||||
m_state.rs.state = nullptr;
|
||||
m_state.rs.numViewports = 0;
|
||||
m_state.rs.numScissors = 0;
|
||||
|
||||
for (uint32_t i = 0; i < D3D11_VIEWPORT_AND_SCISSORRECT_OBJECT_COUNT_PER_PIPELINE; i++) {
|
||||
m_state.rs.viewports[i] = D3D11_VIEWPORT { };
|
||||
m_state.rs.scissors [i] = D3D11_RECT { };
|
||||
}
|
||||
|
||||
// Default SO state
|
||||
for (uint32_t i = 0; i < D3D11_SO_BUFFER_SLOT_COUNT; i++) {
|
||||
m_state.so.targets[i].buffer = nullptr;
|
||||
m_state.so.targets[i].offset = 0;
|
||||
}
|
||||
|
||||
// Default predication
|
||||
m_state.pr.predicateObject = nullptr;
|
||||
m_state.pr.predicateValue = FALSE;
|
||||
|
||||
// Make sure to apply all state
|
||||
ResetState();
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::SetPredication(
|
||||
ID3D11Predicate* pPredicate,
|
||||
BOOL PredicateValue) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
auto predicate = D3D11Query::FromPredicate(pPredicate);
|
||||
m_state.pr.predicateObject = predicate;
|
||||
m_state.pr.predicateValue = PredicateValue;
|
||||
|
||||
static bool s_errorShown = false;
|
||||
|
||||
if (pPredicate && !std::exchange(s_errorShown, true))
|
||||
Logger::err("D3D11DeviceContext::SetPredication: Stub");
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::GetPredication(
|
||||
ID3D11Predicate** ppPredicate,
|
||||
BOOL* pPredicateValue) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
if (ppPredicate)
|
||||
*ppPredicate = D3D11Query::AsPredicate(m_state.pr.predicateObject.ref());
|
||||
|
||||
if (pPredicateValue)
|
||||
*pPredicateValue = m_state.pr.predicateValue;
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::CopySubresourceRegion(
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::CopySubresourceRegion(
|
||||
ID3D11Resource* pDstResource,
|
||||
UINT DstSubresource,
|
||||
UINT DstX,
|
||||
@ -303,9 +184,10 @@ namespace dxvk {
|
||||
pDstResource, DstSubresource, DstX, DstY, DstZ,
|
||||
pSrcResource, SrcSubresource, pSrcBox, 0);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::CopySubresourceRegion1(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::CopySubresourceRegion1(
|
||||
ID3D11Resource* pDstResource,
|
||||
UINT DstSubresource,
|
||||
UINT DstX,
|
||||
@ -328,10 +210,10 @@ namespace dxvk {
|
||||
|
||||
D3D11_RESOURCE_DIMENSION dstResourceDim = D3D11_RESOURCE_DIMENSION_UNKNOWN;
|
||||
D3D11_RESOURCE_DIMENSION srcResourceDim = D3D11_RESOURCE_DIMENSION_UNKNOWN;
|
||||
|
||||
|
||||
pDstResource->GetType(&dstResourceDim);
|
||||
pSrcResource->GetType(&srcResourceDim);
|
||||
|
||||
|
||||
if (dstResourceDim == D3D11_RESOURCE_DIMENSION_BUFFER && srcResourceDim == D3D11_RESOURCE_DIMENSION_BUFFER) {
|
||||
auto dstBuffer = static_cast<D3D11Buffer*>(pDstResource);
|
||||
auto srcBuffer = static_cast<D3D11Buffer*>(pSrcResource);
|
||||
@ -339,84 +221,75 @@ namespace dxvk {
|
||||
VkDeviceSize dstOffset = DstX;
|
||||
VkDeviceSize srcOffset = 0;
|
||||
VkDeviceSize byteCount = -1;
|
||||
|
||||
|
||||
if (pSrcBox) {
|
||||
srcOffset = pSrcBox->left;
|
||||
byteCount = pSrcBox->right - pSrcBox->left;
|
||||
}
|
||||
|
||||
|
||||
CopyBuffer(dstBuffer, dstOffset, srcBuffer, srcOffset, byteCount);
|
||||
} else if (dstResourceDim != D3D11_RESOURCE_DIMENSION_BUFFER && srcResourceDim != D3D11_RESOURCE_DIMENSION_BUFFER) {
|
||||
auto dstTexture = GetCommonTexture(pDstResource);
|
||||
auto srcTexture = GetCommonTexture(pSrcResource);
|
||||
|
||||
|
||||
if (DstSubresource >= dstTexture->CountSubresources()
|
||||
|| SrcSubresource >= srcTexture->CountSubresources())
|
||||
return;
|
||||
|
||||
auto dstFormatInfo = imageFormatInfo(dstTexture->GetPackedFormat());
|
||||
auto srcFormatInfo = imageFormatInfo(srcTexture->GetPackedFormat());
|
||||
|
||||
|
||||
auto dstFormatInfo = lookupFormatInfo(dstTexture->GetPackedFormat());
|
||||
auto srcFormatInfo = lookupFormatInfo(srcTexture->GetPackedFormat());
|
||||
|
||||
auto dstLayers = vk::makeSubresourceLayers(dstTexture->GetSubresourceFromIndex(dstFormatInfo->aspectMask, DstSubresource));
|
||||
auto srcLayers = vk::makeSubresourceLayers(srcTexture->GetSubresourceFromIndex(srcFormatInfo->aspectMask, SrcSubresource));
|
||||
|
||||
|
||||
VkOffset3D srcOffset = { 0, 0, 0 };
|
||||
VkOffset3D dstOffset = { int32_t(DstX), int32_t(DstY), int32_t(DstZ) };
|
||||
|
||||
|
||||
VkExtent3D srcExtent = srcTexture->MipLevelExtent(srcLayers.mipLevel);
|
||||
|
||||
if (pSrcBox != nullptr) {
|
||||
|
||||
if (pSrcBox) {
|
||||
srcOffset.x = pSrcBox->left;
|
||||
srcOffset.y = pSrcBox->top;
|
||||
srcOffset.z = pSrcBox->front;
|
||||
|
||||
|
||||
srcExtent.width = pSrcBox->right - pSrcBox->left;
|
||||
srcExtent.height = pSrcBox->bottom - pSrcBox->top;
|
||||
srcExtent.depth = pSrcBox->back - pSrcBox->front;
|
||||
}
|
||||
|
||||
|
||||
CopyImage(
|
||||
dstTexture, &dstLayers, dstOffset,
|
||||
srcTexture, &srcLayers, srcOffset,
|
||||
srcExtent);
|
||||
} else {
|
||||
Logger::err(str::format(
|
||||
"D3D11: CopySubresourceRegion1: Incompatible resources",
|
||||
"\n Dst resource type: ", dstResourceDim,
|
||||
"\n Src resource type: ", srcResourceDim));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::CopyResource(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::CopyResource(
|
||||
ID3D11Resource* pDstResource,
|
||||
ID3D11Resource* pSrcResource) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
if (!pDstResource || !pSrcResource || (pDstResource == pSrcResource))
|
||||
return;
|
||||
|
||||
|
||||
D3D11_RESOURCE_DIMENSION dstResourceDim = D3D11_RESOURCE_DIMENSION_UNKNOWN;
|
||||
D3D11_RESOURCE_DIMENSION srcResourceDim = D3D11_RESOURCE_DIMENSION_UNKNOWN;
|
||||
|
||||
|
||||
pDstResource->GetType(&dstResourceDim);
|
||||
pSrcResource->GetType(&srcResourceDim);
|
||||
|
||||
if (dstResourceDim != srcResourceDim) {
|
||||
Logger::err(str::format(
|
||||
"D3D11: CopyResource: Incompatible resources",
|
||||
"\n Dst resource type: ", dstResourceDim,
|
||||
"\n Src resource type: ", srcResourceDim));
|
||||
|
||||
if (dstResourceDim != srcResourceDim)
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
if (dstResourceDim == D3D11_RESOURCE_DIMENSION_BUFFER) {
|
||||
auto dstBuffer = static_cast<D3D11Buffer*>(pDstResource);
|
||||
auto srcBuffer = static_cast<D3D11Buffer*>(pSrcResource);
|
||||
|
||||
if (dstBuffer->Desc()->ByteWidth != srcBuffer->Desc()->ByteWidth)
|
||||
return;
|
||||
|
||||
|
||||
CopyBuffer(dstBuffer, 0, srcBuffer, 0, -1);
|
||||
} else {
|
||||
auto dstTexture = GetCommonTexture(pDstResource);
|
||||
@ -427,18 +300,16 @@ namespace dxvk {
|
||||
|
||||
// The subresource count must match as well
|
||||
if (dstDesc->ArraySize != srcDesc->ArraySize
|
||||
|| dstDesc->MipLevels != srcDesc->MipLevels) {
|
||||
Logger::err("D3D11: CopyResource: Incompatible images");
|
||||
|| dstDesc->MipLevels != srcDesc->MipLevels)
|
||||
return;
|
||||
}
|
||||
|
||||
auto dstFormatInfo = imageFormatInfo(dstTexture->GetPackedFormat());
|
||||
auto srcFormatInfo = imageFormatInfo(srcTexture->GetPackedFormat());
|
||||
auto dstFormatInfo = lookupFormatInfo(dstTexture->GetPackedFormat());
|
||||
auto srcFormatInfo = lookupFormatInfo(srcTexture->GetPackedFormat());
|
||||
|
||||
for (uint32_t i = 0; i < dstDesc->MipLevels; i++) {
|
||||
VkImageSubresourceLayers dstLayers = { dstFormatInfo->aspectMask, i, 0, dstDesc->ArraySize };
|
||||
VkImageSubresourceLayers srcLayers = { srcFormatInfo->aspectMask, i, 0, srcDesc->ArraySize };
|
||||
|
||||
|
||||
CopyImage(
|
||||
dstTexture, &dstLayers, VkOffset3D(),
|
||||
srcTexture, &srcLayers, VkOffset3D(),
|
||||
@ -448,7 +319,8 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::CopyStructureCount(
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::CopyStructureCount(
|
||||
ID3D11Buffer* pDstBuffer,
|
||||
UINT DstAlignedByteOffset,
|
||||
ID3D11UnorderedAccessView* pSrcView) {
|
||||
@ -460,13 +332,14 @@ namespace dxvk {
|
||||
if (!buf || !uav)
|
||||
return;
|
||||
|
||||
auto counterSlice = uav->GetCounterSlice();
|
||||
if (!counterSlice.defined())
|
||||
auto counterView = uav->GetCounterView();
|
||||
|
||||
if (counterView == nullptr)
|
||||
return;
|
||||
|
||||
EmitCs([
|
||||
cDstSlice = buf->GetBufferSlice(DstAlignedByteOffset),
|
||||
cSrcSlice = std::move(counterSlice)
|
||||
cSrcSlice = counterView->slice()
|
||||
] (DxvkContext* ctx) {
|
||||
ctx->copyBuffer(
|
||||
cDstSlice.buffer(),
|
||||
@ -477,72 +350,24 @@ namespace dxvk {
|
||||
});
|
||||
|
||||
if (buf->HasSequenceNumber())
|
||||
TrackBufferSequenceNumber(buf);
|
||||
GetTypedContext()->TrackBufferSequenceNumber(buf);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::CopyTiles(
|
||||
ID3D11Resource* pTiledResource,
|
||||
const D3D11_TILED_RESOURCE_COORDINATE* pTileRegionStartCoordinate,
|
||||
const D3D11_TILE_REGION_SIZE* pTileRegionSize,
|
||||
ID3D11Buffer* pBuffer,
|
||||
UINT64 BufferStartOffsetInBytes,
|
||||
UINT Flags) {
|
||||
static bool s_errorShown = false;
|
||||
|
||||
if (!std::exchange(s_errorShown, true))
|
||||
Logger::err("D3D11DeviceContext::CopyTiles: Not implemented");
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D11DeviceContext::CopyTileMappings(
|
||||
ID3D11Resource* pDestTiledResource,
|
||||
const D3D11_TILED_RESOURCE_COORDINATE* pDestRegionStartCoordinate,
|
||||
ID3D11Resource* pSourceTiledResource,
|
||||
const D3D11_TILED_RESOURCE_COORDINATE* pSourceRegionStartCoordinate,
|
||||
const D3D11_TILE_REGION_SIZE* pTileRegionSize,
|
||||
UINT Flags) {
|
||||
static bool s_errorShown = false;
|
||||
|
||||
if (!std::exchange(s_errorShown, true))
|
||||
Logger::err("D3D11DeviceContext::CopyTileMappings: Not implemented");
|
||||
|
||||
return DXGI_ERROR_INVALID_CALL;
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D11DeviceContext::ResizeTilePool(
|
||||
ID3D11Buffer* pTilePool,
|
||||
UINT64 NewSizeInBytes) {
|
||||
static bool s_errorShown = false;
|
||||
|
||||
if (!std::exchange(s_errorShown, true))
|
||||
Logger::err("D3D11DeviceContext::ResizeTilePool: Not implemented");
|
||||
|
||||
return DXGI_ERROR_INVALID_CALL;
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::TiledResourceBarrier(
|
||||
ID3D11DeviceChild* pTiledResourceOrViewAccessBeforeBarrier,
|
||||
ID3D11DeviceChild* pTiledResourceOrViewAccessAfterBarrier) {
|
||||
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::ClearRenderTargetView(
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::ClearRenderTargetView(
|
||||
ID3D11RenderTargetView* pRenderTargetView,
|
||||
const FLOAT ColorRGBA[4]) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
auto rtv = static_cast<D3D11RenderTargetView*>(pRenderTargetView);
|
||||
|
||||
|
||||
if (!rtv)
|
||||
return;
|
||||
|
||||
|
||||
auto view = rtv->GetImageView();
|
||||
auto color = ConvertColorValue(ColorRGBA, view->formatInfo());
|
||||
|
||||
|
||||
EmitCs([
|
||||
cClearValue = color,
|
||||
cImageView = std::move(view)
|
||||
@ -553,26 +378,27 @@ namespace dxvk {
|
||||
cClearValue);
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::ClearUnorderedAccessViewUint(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::ClearUnorderedAccessViewUint(
|
||||
ID3D11UnorderedAccessView* pUnorderedAccessView,
|
||||
const UINT Values[4]) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
auto uav = static_cast<D3D11UnorderedAccessView*>(pUnorderedAccessView);
|
||||
|
||||
|
||||
if (!uav)
|
||||
return;
|
||||
|
||||
|
||||
// Gather UAV format info. We'll use this to determine
|
||||
// whether we need to create a temporary view or not.
|
||||
D3D11_UNORDERED_ACCESS_VIEW_DESC uavDesc;
|
||||
uav->GetDesc(&uavDesc);
|
||||
|
||||
|
||||
VkFormat uavFormat = m_parent->LookupFormat(uavDesc.Format, DXGI_VK_FORMAT_MODE_ANY).Format;
|
||||
VkFormat rawFormat = m_parent->LookupFormat(uavDesc.Format, DXGI_VK_FORMAT_MODE_RAW).Format;
|
||||
|
||||
|
||||
if (uavFormat != rawFormat && rawFormat == VK_FORMAT_UNDEFINED) {
|
||||
Logger::err(str::format("D3D11: ClearUnorderedAccessViewUint: No raw format found for ", uavFormat));
|
||||
return;
|
||||
@ -580,15 +406,22 @@ namespace dxvk {
|
||||
|
||||
VkClearValue clearValue;
|
||||
|
||||
// R11G11B10 is a special case since there's no corresponding
|
||||
// integer format with the same bit layout. Use R32 instead.
|
||||
if (uavFormat == VK_FORMAT_B10G11R11_UFLOAT_PACK32) {
|
||||
if (uavDesc.Format == DXGI_FORMAT_R11G11B10_FLOAT) {
|
||||
// R11G11B10 is a special case since there's no corresponding
|
||||
// integer format with the same bit layout. Use R32 instead.
|
||||
clearValue.color.uint32[0] = ((Values[0] & 0x7FF) << 0)
|
||||
| ((Values[1] & 0x7FF) << 11)
|
||||
| ((Values[2] & 0x3FF) << 22);
|
||||
clearValue.color.uint32[1] = 0;
|
||||
clearValue.color.uint32[2] = 0;
|
||||
clearValue.color.uint32[3] = 0;
|
||||
} else if (uavDesc.Format == DXGI_FORMAT_A8_UNORM) {
|
||||
// We need to use R8_UINT to clear A8_UNORM images,
|
||||
// so remap the alpha component to the red channel.
|
||||
clearValue.color.uint32[0] = Values[3];
|
||||
clearValue.color.uint32[1] = 0;
|
||||
clearValue.color.uint32[2] = 0;
|
||||
clearValue.color.uint32[3] = 0;
|
||||
} else {
|
||||
clearValue.color.uint32[0] = Values[0];
|
||||
clearValue.color.uint32[1] = Values[1];
|
||||
@ -601,7 +434,7 @@ namespace dxvk {
|
||||
// buffers that can be used for atomic operations, we can
|
||||
// use the fast Vulkan buffer clear function.
|
||||
Rc<DxvkBufferView> bufferView = uav->GetBufferView();
|
||||
|
||||
|
||||
if (bufferView->info().format == VK_FORMAT_R32_UINT
|
||||
|| bufferView->info().format == VK_FORMAT_R32_SINT
|
||||
|| bufferView->info().format == VK_FORMAT_R32_SFLOAT
|
||||
@ -621,11 +454,11 @@ namespace dxvk {
|
||||
if (uavFormat != rawFormat) {
|
||||
DxvkBufferViewCreateInfo info = bufferView->info();
|
||||
info.format = rawFormat;
|
||||
|
||||
|
||||
bufferView = m_device->createBufferView(
|
||||
bufferView->buffer(), info);
|
||||
}
|
||||
|
||||
|
||||
EmitCs([
|
||||
cClearValue = clearValue,
|
||||
cDstView = bufferView
|
||||
@ -661,10 +494,10 @@ namespace dxvk {
|
||||
if (uavFormat != rawFormat && !isZeroClearValue) {
|
||||
DxvkImageViewCreateInfo info = imageView->info();
|
||||
info.format = rawFormat;
|
||||
|
||||
|
||||
imageView = m_device->createImageView(imageView->image(), info);
|
||||
}
|
||||
|
||||
|
||||
EmitCs([
|
||||
cClearValue = clearValue,
|
||||
cDstView = imageView
|
||||
@ -717,18 +550,19 @@ namespace dxvk {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::ClearUnorderedAccessViewFloat(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::ClearUnorderedAccessViewFloat(
|
||||
ID3D11UnorderedAccessView* pUnorderedAccessView,
|
||||
const FLOAT Values[4]) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
auto uav = static_cast<D3D11UnorderedAccessView*>(pUnorderedAccessView);
|
||||
|
||||
|
||||
if (!uav)
|
||||
return;
|
||||
|
||||
|
||||
auto imgView = uav->GetImageView();
|
||||
auto bufView = uav->GetBufferView();
|
||||
|
||||
@ -738,13 +572,13 @@ namespace dxvk {
|
||||
|
||||
if (!info || info->flags.any(DxvkFormatFlag::SampledSInt, DxvkFormatFlag::SampledUInt))
|
||||
return;
|
||||
|
||||
|
||||
VkClearValue clearValue;
|
||||
clearValue.color.float32[0] = Values[0];
|
||||
clearValue.color.float32[1] = Values[1];
|
||||
clearValue.color.float32[2] = Values[2];
|
||||
clearValue.color.float32[3] = Values[3];
|
||||
|
||||
|
||||
if (uav->GetResourceType() == D3D11_RESOURCE_DIMENSION_BUFFER) {
|
||||
EmitCs([
|
||||
cClearValue = clearValue,
|
||||
@ -768,9 +602,10 @@ namespace dxvk {
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::ClearDepthStencilView(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::ClearDepthStencilView(
|
||||
ID3D11DepthStencilView* pDepthStencilView,
|
||||
UINT ClearFlags,
|
||||
FLOAT Depth,
|
||||
@ -778,29 +613,29 @@ namespace dxvk {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
auto dsv = static_cast<D3D11DepthStencilView*>(pDepthStencilView);
|
||||
|
||||
|
||||
if (!dsv)
|
||||
return;
|
||||
|
||||
|
||||
// Figure out which aspects to clear based on
|
||||
// the image view properties and clear flags.
|
||||
VkImageAspectFlags aspectMask = 0;
|
||||
|
||||
|
||||
if (ClearFlags & D3D11_CLEAR_DEPTH)
|
||||
aspectMask |= VK_IMAGE_ASPECT_DEPTH_BIT;
|
||||
|
||||
|
||||
if (ClearFlags & D3D11_CLEAR_STENCIL)
|
||||
aspectMask |= VK_IMAGE_ASPECT_STENCIL_BIT;
|
||||
|
||||
|
||||
aspectMask &= dsv->GetWritableAspectMask();
|
||||
|
||||
if (!aspectMask)
|
||||
return;
|
||||
|
||||
|
||||
VkClearValue clearValue;
|
||||
clearValue.depthStencil.depth = Depth;
|
||||
clearValue.depthStencil.stencil = Stencil;
|
||||
|
||||
|
||||
EmitCs([
|
||||
cClearValue = clearValue,
|
||||
cAspectMask = aspectMask,
|
||||
@ -812,12 +647,13 @@ namespace dxvk {
|
||||
cClearValue);
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::ClearView(
|
||||
ID3D11View* pView,
|
||||
const FLOAT Color[4],
|
||||
const D3D11_RECT* pRect,
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::ClearView(
|
||||
ID3D11View* pView,
|
||||
const FLOAT Color[4],
|
||||
const D3D11_RECT* pRect,
|
||||
UINT NumRects) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
@ -840,7 +676,7 @@ namespace dxvk {
|
||||
|
||||
if (rtv != nullptr)
|
||||
imgView = rtv->GetImageView();
|
||||
|
||||
|
||||
if (uav != nullptr) {
|
||||
bufView = uav->GetBufferView();
|
||||
imgView = uav->GetImageView();
|
||||
@ -860,16 +696,16 @@ namespace dxvk {
|
||||
|
||||
if (bufView != nullptr)
|
||||
format = bufView->info().format;
|
||||
|
||||
|
||||
if (imgView != nullptr)
|
||||
format = imgView->info().format;
|
||||
|
||||
|
||||
if (format == VK_FORMAT_UNDEFINED)
|
||||
return;
|
||||
|
||||
|
||||
// We'll need the format info to determine the buffer
|
||||
// element size, and we also need it for depth images.
|
||||
const DxvkFormatInfo* formatInfo = imageFormatInfo(format);
|
||||
const DxvkFormatInfo* formatInfo = lookupFormatInfo(format);
|
||||
|
||||
// Convert the clear color format. ClearView takes
|
||||
// the clear value for integer formats as a set of
|
||||
@ -884,7 +720,7 @@ namespace dxvk {
|
||||
|| pRect[i].top >= pRect[i].bottom)
|
||||
continue;
|
||||
}
|
||||
|
||||
|
||||
if (bufView != nullptr) {
|
||||
VkDeviceSize offset = 0;
|
||||
VkDeviceSize length = bufView->info().rangeLength / formatInfo->elementSize;
|
||||
@ -918,7 +754,7 @@ namespace dxvk {
|
||||
uint32_t(pRect[i].right - pRect[i].left),
|
||||
uint32_t(pRect[i].bottom - pRect[i].top), 1 };
|
||||
}
|
||||
|
||||
|
||||
EmitCs([
|
||||
cImageView = imgView,
|
||||
cAreaOffset = offset,
|
||||
@ -949,9 +785,10 @@ namespace dxvk {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::GenerateMips(ID3D11ShaderResourceView* pShaderResourceView) {
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::GenerateMips(ID3D11ShaderResourceView* pShaderResourceView) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
auto view = static_cast<D3D11ShaderResourceView*>(pShaderResourceView);
|
||||
@ -969,62 +806,10 @@ namespace dxvk {
|
||||
ctx->generateMipmaps(cDstImageView, VK_FILTER_LINEAR);
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D11DeviceContext::UpdateTileMappings(
|
||||
ID3D11Resource* pTiledResource,
|
||||
UINT NumTiledResourceRegions,
|
||||
const D3D11_TILED_RESOURCE_COORDINATE* pTiledResourceRegionStartCoordinates,
|
||||
const D3D11_TILE_REGION_SIZE* pTiledResourceRegionSizes,
|
||||
ID3D11Buffer* pTilePool,
|
||||
UINT NumRanges,
|
||||
const UINT* pRangeFlags,
|
||||
const UINT* pTilePoolStartOffsets,
|
||||
const UINT* pRangeTileCounts,
|
||||
UINT Flags) {
|
||||
bool s_errorShown = false;
|
||||
|
||||
if (std::exchange(s_errorShown, true))
|
||||
Logger::err("D3D11DeviceContext::UpdateTileMappings: Not implemented");
|
||||
|
||||
return DXGI_ERROR_INVALID_CALL;
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::UpdateTiles(
|
||||
ID3D11Resource* pDestTiledResource,
|
||||
const D3D11_TILED_RESOURCE_COORDINATE* pDestTileRegionStartCoordinate,
|
||||
const D3D11_TILE_REGION_SIZE* pDestTileRegionSize,
|
||||
const void* pSourceTileData,
|
||||
UINT Flags) {
|
||||
bool s_errorShown = false;
|
||||
|
||||
if (std::exchange(s_errorShown, true))
|
||||
Logger::err("D3D11DeviceContext::UpdateTiles: Not implemented");
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::SetResourceMinLOD(
|
||||
ID3D11Resource* pResource,
|
||||
FLOAT MinLOD) {
|
||||
bool s_errorShown = false;
|
||||
|
||||
if (std::exchange(s_errorShown, true))
|
||||
Logger::err("D3D11DeviceContext::SetResourceMinLOD: Not implemented");
|
||||
}
|
||||
|
||||
|
||||
FLOAT STDMETHODCALLTYPE D3D11DeviceContext::GetResourceMinLOD(ID3D11Resource* pResource) {
|
||||
bool s_errorShown = false;
|
||||
|
||||
if (std::exchange(s_errorShown, true))
|
||||
Logger::err("D3D11DeviceContext::GetResourceMinLOD: Not implemented");
|
||||
|
||||
return 0.0f;
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::ResolveSubresource(
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::ResolveSubresource(
|
||||
ID3D11Resource* pDstResource,
|
||||
UINT DstSubresource,
|
||||
ID3D11Resource* pSrcResource,
|
||||
@ -1034,73 +819,63 @@ namespace dxvk {
|
||||
|
||||
bool isSameSubresource = pDstResource == pSrcResource
|
||||
&& DstSubresource == SrcSubresource;
|
||||
|
||||
|
||||
if (!pDstResource || !pSrcResource || isSameSubresource)
|
||||
return;
|
||||
|
||||
|
||||
D3D11_RESOURCE_DIMENSION dstResourceType;
|
||||
D3D11_RESOURCE_DIMENSION srcResourceType;
|
||||
|
||||
|
||||
pDstResource->GetType(&dstResourceType);
|
||||
pSrcResource->GetType(&srcResourceType);
|
||||
|
||||
|
||||
if (dstResourceType != D3D11_RESOURCE_DIMENSION_TEXTURE2D
|
||||
|| srcResourceType != D3D11_RESOURCE_DIMENSION_TEXTURE2D) {
|
||||
Logger::err(str::format(
|
||||
"D3D11: ResolveSubresource: Incompatible resources",
|
||||
"\n Dst resource type: ", dstResourceType,
|
||||
"\n Src resource type: ", srcResourceType));
|
||||
|| srcResourceType != D3D11_RESOURCE_DIMENSION_TEXTURE2D)
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
auto dstTexture = static_cast<D3D11Texture2D*>(pDstResource);
|
||||
auto srcTexture = static_cast<D3D11Texture2D*>(pSrcResource);
|
||||
|
||||
|
||||
D3D11_TEXTURE2D_DESC dstDesc;
|
||||
D3D11_TEXTURE2D_DESC srcDesc;
|
||||
|
||||
|
||||
dstTexture->GetDesc(&dstDesc);
|
||||
srcTexture->GetDesc(&srcDesc);
|
||||
|
||||
if (dstDesc.SampleDesc.Count != 1) {
|
||||
Logger::err(str::format(
|
||||
"D3D11: ResolveSubresource: Invalid sample counts",
|
||||
"\n Dst sample count: ", dstDesc.SampleDesc.Count,
|
||||
"\n Src sample count: ", srcDesc.SampleDesc.Count));
|
||||
|
||||
if (dstDesc.SampleDesc.Count != 1)
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
D3D11CommonTexture* dstTextureInfo = GetCommonTexture(pDstResource);
|
||||
D3D11CommonTexture* srcTextureInfo = GetCommonTexture(pSrcResource);
|
||||
|
||||
|
||||
const DXGI_VK_FORMAT_INFO dstFormatInfo = m_parent->LookupFormat(dstDesc.Format, DXGI_VK_FORMAT_MODE_ANY);
|
||||
const DXGI_VK_FORMAT_INFO srcFormatInfo = m_parent->LookupFormat(srcDesc.Format, DXGI_VK_FORMAT_MODE_ANY);
|
||||
|
||||
auto dstVulkanFormatInfo = imageFormatInfo(dstFormatInfo.Format);
|
||||
auto srcVulkanFormatInfo = imageFormatInfo(srcFormatInfo.Format);
|
||||
|
||||
|
||||
auto dstVulkanFormatInfo = lookupFormatInfo(dstFormatInfo.Format);
|
||||
auto srcVulkanFormatInfo = lookupFormatInfo(srcFormatInfo.Format);
|
||||
|
||||
if (DstSubresource >= dstTextureInfo->CountSubresources()
|
||||
|| SrcSubresource >= srcTextureInfo->CountSubresources())
|
||||
return;
|
||||
|
||||
|
||||
const VkImageSubresource dstSubresource =
|
||||
dstTextureInfo->GetSubresourceFromIndex(
|
||||
dstVulkanFormatInfo->aspectMask, DstSubresource);
|
||||
|
||||
|
||||
const VkImageSubresource srcSubresource =
|
||||
srcTextureInfo->GetSubresourceFromIndex(
|
||||
srcVulkanFormatInfo->aspectMask, SrcSubresource);
|
||||
|
||||
|
||||
const VkImageSubresourceLayers dstSubresourceLayers = {
|
||||
dstSubresource.aspectMask,
|
||||
dstSubresource.mipLevel,
|
||||
dstSubresource.arrayLayer, 1 };
|
||||
|
||||
|
||||
const VkImageSubresourceLayers srcSubresourceLayers = {
|
||||
srcSubresource.aspectMask,
|
||||
srcSubresource.mipLevel,
|
||||
srcSubresource.arrayLayer, 1 };
|
||||
|
||||
|
||||
if (srcDesc.SampleDesc.Count == 1 || m_parent->GetOptions()->disableMsaa) {
|
||||
EmitCs([
|
||||
cDstImage = dstTextureInfo->GetImage(),
|
||||
@ -1116,7 +891,7 @@ namespace dxvk {
|
||||
} else {
|
||||
const VkFormat format = m_parent->LookupFormat(
|
||||
Format, DXGI_VK_FORMAT_MODE_ANY).Format;
|
||||
|
||||
|
||||
EmitCs([
|
||||
cDstImage = dstTextureInfo->GetImage(),
|
||||
cSrcImage = srcTextureInfo->GetImage(),
|
||||
@ -1136,18 +911,46 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
if (dstTextureInfo->HasSequenceNumber())
|
||||
TrackTextureSequenceNumber(dstTextureInfo, DstSubresource);
|
||||
GetTypedContext()->TrackTextureSequenceNumber(dstTextureInfo, DstSubresource);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::DrawAuto() {
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::UpdateSubresource(
|
||||
ID3D11Resource* pDstResource,
|
||||
UINT DstSubresource,
|
||||
const D3D11_BOX* pDstBox,
|
||||
const void* pSrcData,
|
||||
UINT SrcRowPitch,
|
||||
UINT SrcDepthPitch) {
|
||||
UpdateResource(pDstResource, DstSubresource, pDstBox,
|
||||
pSrcData, SrcRowPitch, SrcDepthPitch, 0);
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::UpdateSubresource1(
|
||||
ID3D11Resource* pDstResource,
|
||||
UINT DstSubresource,
|
||||
const D3D11_BOX* pDstBox,
|
||||
const void* pSrcData,
|
||||
UINT SrcRowPitch,
|
||||
UINT SrcDepthPitch,
|
||||
UINT CopyFlags) {
|
||||
UpdateResource(pDstResource, DstSubresource, pDstBox,
|
||||
pSrcData, SrcRowPitch, SrcDepthPitch, CopyFlags);
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::DrawAuto() {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
D3D11Buffer* buffer = m_state.ia.vertexBuffers[0].buffer.ptr();
|
||||
|
||||
if (buffer == nullptr)
|
||||
if (!buffer)
|
||||
return;
|
||||
|
||||
|
||||
DxvkBufferSlice vtxBuf = buffer->GetBufferSlice();
|
||||
DxvkBufferSlice ctrBuf = buffer->GetSOCounter();
|
||||
|
||||
@ -1160,9 +963,10 @@ namespace dxvk {
|
||||
vtxBuf.offset());
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::Draw(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::Draw(
|
||||
UINT VertexCount,
|
||||
UINT StartVertexLocation) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
@ -1173,14 +977,15 @@ namespace dxvk {
|
||||
StartVertexLocation, 0);
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::DrawIndexed(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::DrawIndexed(
|
||||
UINT IndexCount,
|
||||
UINT StartIndexLocation,
|
||||
INT BaseVertexLocation) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
EmitCs([=] (DxvkContext* ctx) {
|
||||
ctx->drawIndexed(
|
||||
IndexCount, 1,
|
||||
@ -1188,15 +993,16 @@ namespace dxvk {
|
||||
BaseVertexLocation, 0);
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::DrawInstanced(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::DrawInstanced(
|
||||
UINT VertexCountPerInstance,
|
||||
UINT InstanceCount,
|
||||
UINT StartVertexLocation,
|
||||
UINT StartInstanceLocation) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
EmitCs([=] (DxvkContext* ctx) {
|
||||
ctx->draw(
|
||||
VertexCountPerInstance,
|
||||
@ -1205,16 +1011,17 @@ namespace dxvk {
|
||||
StartInstanceLocation);
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::DrawIndexedInstanced(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::DrawIndexedInstanced(
|
||||
UINT IndexCountPerInstance,
|
||||
UINT InstanceCount,
|
||||
UINT StartIndexLocation,
|
||||
INT BaseVertexLocation,
|
||||
UINT StartInstanceLocation) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
EmitCs([=] (DxvkContext* ctx) {
|
||||
ctx->drawIndexed(
|
||||
IndexCountPerInstance,
|
||||
@ -1224,9 +1031,10 @@ namespace dxvk {
|
||||
StartInstanceLocation);
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::DrawIndexedInstancedIndirect(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::DrawIndexedInstancedIndirect(
|
||||
ID3D11Buffer* pBufferForArgs,
|
||||
UINT AlignedByteOffsetForArgs) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
@ -1234,15 +1042,15 @@ namespace dxvk {
|
||||
|
||||
if (!ValidateDrawBufferSize(pBufferForArgs, AlignedByteOffsetForArgs, sizeof(VkDrawIndexedIndirectCommand)))
|
||||
return;
|
||||
|
||||
|
||||
// If possible, batch up multiple indirect draw calls of
|
||||
// the same type into one single multiDrawIndirect call
|
||||
auto cmdData = static_cast<D3D11CmdDrawIndirectData*>(m_cmdData);
|
||||
auto stride = 0u;
|
||||
|
||||
|
||||
if (cmdData && cmdData->type == D3D11CmdType::DrawIndirectIndexed)
|
||||
stride = GetIndirectCommandStride(cmdData, AlignedByteOffsetForArgs, sizeof(VkDrawIndexedIndirectCommand));
|
||||
|
||||
|
||||
if (stride) {
|
||||
cmdData->count += 1;
|
||||
cmdData->stride = stride;
|
||||
@ -1251,16 +1059,17 @@ namespace dxvk {
|
||||
[] (DxvkContext* ctx, const D3D11CmdDrawIndirectData* data) {
|
||||
ctx->drawIndexedIndirect(data->offset, data->count, data->stride);
|
||||
});
|
||||
|
||||
|
||||
cmdData->type = D3D11CmdType::DrawIndirectIndexed;
|
||||
cmdData->offset = AlignedByteOffsetForArgs;
|
||||
cmdData->count = 1;
|
||||
cmdData->stride = 0;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::DrawInstancedIndirect(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::DrawInstancedIndirect(
|
||||
ID3D11Buffer* pBufferForArgs,
|
||||
UINT AlignedByteOffsetForArgs) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
@ -1273,10 +1082,10 @@ namespace dxvk {
|
||||
// the same type into one single multiDrawIndirect call
|
||||
auto cmdData = static_cast<D3D11CmdDrawIndirectData*>(m_cmdData);
|
||||
auto stride = 0u;
|
||||
|
||||
|
||||
if (cmdData && cmdData->type == D3D11CmdType::DrawIndirect)
|
||||
stride = GetIndirectCommandStride(cmdData, AlignedByteOffsetForArgs, sizeof(VkDrawIndirectCommand));
|
||||
|
||||
|
||||
if (stride) {
|
||||
cmdData->count += 1;
|
||||
cmdData->stride = stride;
|
||||
@ -1285,21 +1094,22 @@ namespace dxvk {
|
||||
[] (DxvkContext* ctx, const D3D11CmdDrawIndirectData* data) {
|
||||
ctx->drawIndirect(data->offset, data->count, data->stride);
|
||||
});
|
||||
|
||||
|
||||
cmdData->type = D3D11CmdType::DrawIndirect;
|
||||
cmdData->offset = AlignedByteOffsetForArgs;
|
||||
cmdData->count = 1;
|
||||
cmdData->stride = 0;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::Dispatch(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::Dispatch(
|
||||
UINT ThreadGroupCountX,
|
||||
UINT ThreadGroupCountY,
|
||||
UINT ThreadGroupCountZ) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
EmitCs([=] (DxvkContext* ctx) {
|
||||
ctx->dispatch(
|
||||
ThreadGroupCountX,
|
||||
@ -1307,14 +1117,15 @@ namespace dxvk {
|
||||
ThreadGroupCountZ);
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::DispatchIndirect(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::DispatchIndirect(
|
||||
ID3D11Buffer* pBufferForArgs,
|
||||
UINT AlignedByteOffsetForArgs) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
SetDrawBuffers(pBufferForArgs, nullptr);
|
||||
|
||||
|
||||
if (!ValidateDrawBufferSize(pBufferForArgs, AlignedByteOffsetForArgs, sizeof(VkDispatchIndirectCommand)))
|
||||
return;
|
||||
|
||||
@ -1323,941 +1134,929 @@ namespace dxvk {
|
||||
ctx->dispatchIndirect(cOffset);
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::IASetInputLayout(ID3D11InputLayout* pInputLayout) {
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::IASetInputLayout(ID3D11InputLayout* pInputLayout) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
auto inputLayout = static_cast<D3D11InputLayout*>(pInputLayout);
|
||||
|
||||
|
||||
if (m_state.ia.inputLayout != inputLayout) {
|
||||
bool equal = false;
|
||||
|
||||
|
||||
// Some games (e.g. Grim Dawn) create lots and lots of
|
||||
// identical input layouts, so we'll only apply the state
|
||||
// if the input layouts has actually changed between calls.
|
||||
if (m_state.ia.inputLayout != nullptr && inputLayout != nullptr)
|
||||
equal = m_state.ia.inputLayout->Compare(inputLayout);
|
||||
|
||||
|
||||
m_state.ia.inputLayout = inputLayout;
|
||||
|
||||
|
||||
if (!equal)
|
||||
ApplyInputLayout();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::IASetPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY Topology) {
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::IASetPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY Topology) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
if (m_state.ia.primitiveTopology != Topology) {
|
||||
m_state.ia.primitiveTopology = Topology;
|
||||
ApplyPrimitiveTopology();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::IASetVertexBuffers(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::IASetVertexBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppVertexBuffers,
|
||||
const UINT* pStrides,
|
||||
const UINT* pOffsets) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
for (uint32_t i = 0; i < NumBuffers; i++) {
|
||||
auto newBuffer = static_cast<D3D11Buffer*>(ppVertexBuffers[i]);
|
||||
bool needsUpdate = m_state.ia.vertexBuffers[StartSlot + i].buffer != newBuffer;
|
||||
|
||||
if (needsUpdate)
|
||||
if (m_state.ia.vertexBuffers[StartSlot + i].buffer != newBuffer) {
|
||||
m_state.ia.vertexBuffers[StartSlot + i].buffer = newBuffer;
|
||||
|
||||
needsUpdate |= m_state.ia.vertexBuffers[StartSlot + i].offset != pOffsets[i]
|
||||
|| m_state.ia.vertexBuffers[StartSlot + i].stride != pStrides[i];
|
||||
|
||||
if (needsUpdate) {
|
||||
m_state.ia.vertexBuffers[StartSlot + i].offset = pOffsets[i];
|
||||
m_state.ia.vertexBuffers[StartSlot + i].stride = pStrides[i];
|
||||
|
||||
BindVertexBuffer(StartSlot + i, newBuffer, pOffsets[i], pStrides[i]);
|
||||
} else if (m_state.ia.vertexBuffers[StartSlot + i].offset != pOffsets[i]
|
||||
|| m_state.ia.vertexBuffers[StartSlot + i].stride != pStrides[i]) {
|
||||
m_state.ia.vertexBuffers[StartSlot + i].offset = pOffsets[i];
|
||||
m_state.ia.vertexBuffers[StartSlot + i].stride = pStrides[i];
|
||||
|
||||
BindVertexBufferRange(StartSlot + i, newBuffer, pOffsets[i], pStrides[i]);
|
||||
}
|
||||
}
|
||||
|
||||
m_state.ia.maxVbCount = std::clamp(StartSlot + NumBuffers,
|
||||
m_state.ia.maxVbCount, uint32_t(m_state.ia.vertexBuffers.size()));
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::IASetIndexBuffer(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::IASetIndexBuffer(
|
||||
ID3D11Buffer* pIndexBuffer,
|
||||
DXGI_FORMAT Format,
|
||||
UINT Offset) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
auto newBuffer = static_cast<D3D11Buffer*>(pIndexBuffer);
|
||||
bool needsUpdate = m_state.ia.indexBuffer.buffer != newBuffer;
|
||||
|
||||
if (needsUpdate)
|
||||
if (m_state.ia.indexBuffer.buffer != newBuffer) {
|
||||
m_state.ia.indexBuffer.buffer = newBuffer;
|
||||
|
||||
needsUpdate |= m_state.ia.indexBuffer.offset != Offset
|
||||
|| m_state.ia.indexBuffer.format != Format;
|
||||
|
||||
if (needsUpdate) {
|
||||
m_state.ia.indexBuffer.offset = Offset;
|
||||
m_state.ia.indexBuffer.format = Format;
|
||||
|
||||
BindIndexBuffer(newBuffer, Offset, Format);
|
||||
} else if (m_state.ia.indexBuffer.offset != Offset
|
||||
|| m_state.ia.indexBuffer.format != Format) {
|
||||
m_state.ia.indexBuffer.offset = Offset;
|
||||
m_state.ia.indexBuffer.format = Format;
|
||||
|
||||
BindIndexBufferRange(newBuffer, Offset, Format);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::IAGetInputLayout(ID3D11InputLayout** ppInputLayout) {
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::IAGetInputLayout(ID3D11InputLayout** ppInputLayout) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
*ppInputLayout = m_state.ia.inputLayout.ref();
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::IAGetPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY* pTopology) {
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::IAGetPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY* pTopology) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
*pTopology = m_state.ia.primitiveTopology;
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::IAGetVertexBuffers(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::IAGetVertexBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppVertexBuffers,
|
||||
UINT* pStrides,
|
||||
UINT* pOffsets) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
for (uint32_t i = 0; i < NumBuffers; i++) {
|
||||
const bool inRange = StartSlot + i < m_state.ia.vertexBuffers.size();
|
||||
|
||||
if (ppVertexBuffers != nullptr) {
|
||||
if (ppVertexBuffers) {
|
||||
ppVertexBuffers[i] = inRange
|
||||
? m_state.ia.vertexBuffers[StartSlot + i].buffer.ref()
|
||||
: nullptr;
|
||||
}
|
||||
|
||||
if (pStrides != nullptr) {
|
||||
|
||||
if (pStrides) {
|
||||
pStrides[i] = inRange
|
||||
? m_state.ia.vertexBuffers[StartSlot + i].stride
|
||||
: 0u;
|
||||
}
|
||||
|
||||
if (pOffsets != nullptr) {
|
||||
|
||||
if (pOffsets) {
|
||||
pOffsets[i] = inRange
|
||||
? m_state.ia.vertexBuffers[StartSlot + i].offset
|
||||
: 0u;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::IAGetIndexBuffer(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::IAGetIndexBuffer(
|
||||
ID3D11Buffer** ppIndexBuffer,
|
||||
DXGI_FORMAT* pFormat,
|
||||
UINT* pOffset) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
if (ppIndexBuffer != nullptr)
|
||||
|
||||
if (ppIndexBuffer)
|
||||
*ppIndexBuffer = m_state.ia.indexBuffer.buffer.ref();
|
||||
|
||||
if (pFormat != nullptr)
|
||||
|
||||
if (pFormat)
|
||||
*pFormat = m_state.ia.indexBuffer.format;
|
||||
|
||||
if (pOffset != nullptr)
|
||||
|
||||
if (pOffset)
|
||||
*pOffset = m_state.ia.indexBuffer.offset;
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::VSSetShader(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::VSSetShader(
|
||||
ID3D11VertexShader* pVertexShader,
|
||||
ID3D11ClassInstance* const* ppClassInstances,
|
||||
UINT NumClassInstances) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
auto shader = static_cast<D3D11VertexShader*>(pVertexShader);
|
||||
|
||||
if (NumClassInstances != 0)
|
||||
|
||||
if (NumClassInstances)
|
||||
Logger::err("D3D11: Class instances not supported");
|
||||
|
||||
if (m_state.vs.shader != shader) {
|
||||
m_state.vs.shader = shader;
|
||||
|
||||
if (m_state.vs != shader) {
|
||||
m_state.vs = shader;
|
||||
|
||||
BindShader<DxbcProgramType::VertexShader>(GetCommonShader(shader));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::VSSetConstantBuffers(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::VSSetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
SetConstantBuffers<DxbcProgramType::VertexShader>(
|
||||
m_state.vs.constantBuffers,
|
||||
StartSlot, NumBuffers,
|
||||
ppConstantBuffers);
|
||||
StartSlot, NumBuffers, ppConstantBuffers);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::VSSetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers,
|
||||
const UINT* pFirstConstant,
|
||||
const UINT* pNumConstants) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
SetConstantBuffers1<DxbcProgramType::VertexShader>(
|
||||
m_state.vs.constantBuffers,
|
||||
StartSlot, NumBuffers,
|
||||
ppConstantBuffers,
|
||||
pFirstConstant,
|
||||
pNumConstants);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::VSSetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView* const* ppShaderResourceViews) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
SetShaderResources<DxbcProgramType::VertexShader>(
|
||||
m_state.vs.shaderResources,
|
||||
StartSlot, NumViews,
|
||||
ppShaderResourceViews);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::VSSetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState* const* ppSamplers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
SetSamplers<DxbcProgramType::VertexShader>(
|
||||
m_state.vs.samplers,
|
||||
StartSlot, NumSamplers,
|
||||
ppSamplers);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::VSGetShader(
|
||||
ID3D11VertexShader** ppVertexShader,
|
||||
ID3D11ClassInstance** ppClassInstances,
|
||||
UINT* pNumClassInstances) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
if (ppVertexShader != nullptr)
|
||||
*ppVertexShader = m_state.vs.shader.ref();
|
||||
|
||||
if (pNumClassInstances != nullptr)
|
||||
*pNumClassInstances = 0;
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::VSGetConstantBuffers(
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::VSSetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppConstantBuffers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetConstantBuffers(
|
||||
m_state.vs.constantBuffers,
|
||||
StartSlot, NumBuffers,
|
||||
ppConstantBuffers,
|
||||
nullptr, nullptr);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::VSGetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppConstantBuffers,
|
||||
UINT* pFirstConstant,
|
||||
UINT* pNumConstants) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetConstantBuffers(
|
||||
m_state.vs.constantBuffers,
|
||||
StartSlot, NumBuffers,
|
||||
ppConstantBuffers,
|
||||
pFirstConstant,
|
||||
pNumConstants);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::VSGetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView** ppShaderResourceViews) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetShaderResources(m_state.vs.shaderResources,
|
||||
StartSlot, NumViews, ppShaderResourceViews);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::VSGetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState** ppSamplers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetSamplers(m_state.vs.samplers,
|
||||
StartSlot, NumSamplers, ppSamplers);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::HSSetShader(
|
||||
ID3D11HullShader* pHullShader,
|
||||
ID3D11ClassInstance* const* ppClassInstances,
|
||||
UINT NumClassInstances) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
auto shader = static_cast<D3D11HullShader*>(pHullShader);
|
||||
|
||||
if (NumClassInstances != 0)
|
||||
Logger::err("D3D11: Class instances not supported");
|
||||
|
||||
if (m_state.hs.shader != shader) {
|
||||
m_state.hs.shader = shader;
|
||||
|
||||
BindShader<DxbcProgramType::HullShader>(GetCommonShader(shader));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::HSSetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView* const* ppShaderResourceViews) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
SetShaderResources<DxbcProgramType::HullShader>(
|
||||
m_state.hs.shaderResources,
|
||||
StartSlot, NumViews,
|
||||
ppShaderResourceViews);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::HSSetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
SetConstantBuffers<DxbcProgramType::HullShader>(
|
||||
m_state.hs.constantBuffers,
|
||||
StartSlot, NumBuffers,
|
||||
ppConstantBuffers);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::HSSetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers,
|
||||
const UINT* pFirstConstant,
|
||||
const UINT* pNumConstants) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
SetConstantBuffers1<DxbcProgramType::HullShader>(
|
||||
m_state.hs.constantBuffers,
|
||||
StartSlot, NumBuffers,
|
||||
ppConstantBuffers,
|
||||
pFirstConstant,
|
||||
pNumConstants);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::HSSetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState* const* ppSamplers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
SetSamplers<DxbcProgramType::HullShader>(
|
||||
m_state.hs.samplers,
|
||||
StartSlot, NumSamplers,
|
||||
ppSamplers);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::HSGetShader(
|
||||
ID3D11HullShader** ppHullShader,
|
||||
ID3D11ClassInstance** ppClassInstances,
|
||||
UINT* pNumClassInstances) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
if (ppHullShader != nullptr)
|
||||
*ppHullShader = m_state.hs.shader.ref();
|
||||
|
||||
if (pNumClassInstances != nullptr)
|
||||
*pNumClassInstances = 0;
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::HSGetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppConstantBuffers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetConstantBuffers(
|
||||
m_state.hs.constantBuffers,
|
||||
StartSlot, NumBuffers,
|
||||
ppConstantBuffers,
|
||||
nullptr, nullptr);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::HSGetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppConstantBuffers,
|
||||
UINT* pFirstConstant,
|
||||
UINT* pNumConstants) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetConstantBuffers(
|
||||
m_state.hs.constantBuffers,
|
||||
StartSlot, NumBuffers,
|
||||
ppConstantBuffers,
|
||||
pFirstConstant,
|
||||
pNumConstants);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::HSGetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView** ppShaderResourceViews) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetShaderResources(m_state.hs.shaderResources,
|
||||
StartSlot, NumViews, ppShaderResourceViews);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::HSGetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState** ppSamplers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetSamplers(m_state.hs.samplers,
|
||||
StartSlot, NumSamplers, ppSamplers);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::DSSetShader(
|
||||
ID3D11DomainShader* pDomainShader,
|
||||
ID3D11ClassInstance* const* ppClassInstances,
|
||||
UINT NumClassInstances) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
auto shader = static_cast<D3D11DomainShader*>(pDomainShader);
|
||||
|
||||
if (NumClassInstances != 0)
|
||||
Logger::err("D3D11: Class instances not supported");
|
||||
|
||||
if (m_state.ds.shader != shader) {
|
||||
m_state.ds.shader = shader;
|
||||
|
||||
BindShader<DxbcProgramType::DomainShader>(GetCommonShader(shader));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::DSSetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView* const* ppShaderResourceViews) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
SetShaderResources<DxbcProgramType::DomainShader>(
|
||||
m_state.ds.shaderResources,
|
||||
StartSlot, NumViews,
|
||||
ppShaderResourceViews);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::DSSetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
SetConstantBuffers<DxbcProgramType::DomainShader>(
|
||||
m_state.ds.constantBuffers,
|
||||
StartSlot, NumBuffers,
|
||||
ppConstantBuffers);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::DSSetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers,
|
||||
const UINT* pFirstConstant,
|
||||
const UINT* pNumConstants) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
SetConstantBuffers1<DxbcProgramType::DomainShader>(
|
||||
m_state.ds.constantBuffers,
|
||||
StartSlot, NumBuffers,
|
||||
ppConstantBuffers,
|
||||
pFirstConstant,
|
||||
pNumConstants);
|
||||
|
||||
SetConstantBuffers1<DxbcProgramType::VertexShader>(
|
||||
StartSlot, NumBuffers, ppConstantBuffers,
|
||||
pFirstConstant, pNumConstants);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::DSSetSamplers(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::VSSetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView* const* ppShaderResourceViews) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
SetShaderResources<DxbcProgramType::VertexShader>(
|
||||
StartSlot, NumViews, ppShaderResourceViews);
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::VSSetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState* const* ppSamplers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
SetSamplers<DxbcProgramType::DomainShader>(
|
||||
m_state.ds.samplers,
|
||||
StartSlot, NumSamplers,
|
||||
ppSamplers);
|
||||
|
||||
SetSamplers<DxbcProgramType::VertexShader>(
|
||||
StartSlot, NumSamplers, ppSamplers);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::DSGetShader(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::VSGetShader(
|
||||
ID3D11VertexShader** ppVertexShader,
|
||||
ID3D11ClassInstance** ppClassInstances,
|
||||
UINT* pNumClassInstances) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
if (ppVertexShader)
|
||||
*ppVertexShader = m_state.vs.ref();
|
||||
|
||||
if (pNumClassInstances)
|
||||
*pNumClassInstances = 0;
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::VSGetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppConstantBuffers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetConstantBuffers<DxbcProgramType::VertexShader>(
|
||||
StartSlot, NumBuffers, ppConstantBuffers,
|
||||
nullptr, nullptr);
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::VSGetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppConstantBuffers,
|
||||
UINT* pFirstConstant,
|
||||
UINT* pNumConstants) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetConstantBuffers<DxbcProgramType::VertexShader>(
|
||||
StartSlot, NumBuffers, ppConstantBuffers,
|
||||
pFirstConstant, pNumConstants);
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::VSGetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView** ppShaderResourceViews) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetShaderResources<DxbcProgramType::VertexShader>(
|
||||
StartSlot, NumViews, ppShaderResourceViews);
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::VSGetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState** ppSamplers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetSamplers<DxbcProgramType::VertexShader>(
|
||||
StartSlot, NumSamplers, ppSamplers);
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::HSSetShader(
|
||||
ID3D11HullShader* pHullShader,
|
||||
ID3D11ClassInstance* const* ppClassInstances,
|
||||
UINT NumClassInstances) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
auto shader = static_cast<D3D11HullShader*>(pHullShader);
|
||||
|
||||
if (NumClassInstances)
|
||||
Logger::err("D3D11: Class instances not supported");
|
||||
|
||||
if (m_state.hs != shader) {
|
||||
m_state.hs = shader;
|
||||
|
||||
BindShader<DxbcProgramType::HullShader>(GetCommonShader(shader));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::HSSetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
SetConstantBuffers<DxbcProgramType::HullShader>(
|
||||
StartSlot, NumBuffers, ppConstantBuffers);
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::HSSetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers,
|
||||
const UINT* pFirstConstant,
|
||||
const UINT* pNumConstants) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
SetConstantBuffers1<DxbcProgramType::HullShader>(
|
||||
StartSlot, NumBuffers, ppConstantBuffers,
|
||||
pFirstConstant, pNumConstants);
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::HSSetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView* const* ppShaderResourceViews) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
SetShaderResources<DxbcProgramType::HullShader>(
|
||||
StartSlot, NumViews, ppShaderResourceViews);
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::HSSetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState* const* ppSamplers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
SetSamplers<DxbcProgramType::HullShader>(
|
||||
StartSlot, NumSamplers, ppSamplers);
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::HSGetShader(
|
||||
ID3D11HullShader** ppHullShader,
|
||||
ID3D11ClassInstance** ppClassInstances,
|
||||
UINT* pNumClassInstances) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
if (ppHullShader)
|
||||
*ppHullShader = m_state.hs.ref();
|
||||
|
||||
if (pNumClassInstances)
|
||||
*pNumClassInstances = 0;
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::HSGetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppConstantBuffers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetConstantBuffers<DxbcProgramType::HullShader>(
|
||||
StartSlot, NumBuffers, ppConstantBuffers,
|
||||
nullptr, nullptr);
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::HSGetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppConstantBuffers,
|
||||
UINT* pFirstConstant,
|
||||
UINT* pNumConstants) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetConstantBuffers<DxbcProgramType::HullShader>(
|
||||
StartSlot, NumBuffers, ppConstantBuffers,
|
||||
pFirstConstant, pNumConstants);
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::HSGetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView** ppShaderResourceViews) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetShaderResources<DxbcProgramType::HullShader>(
|
||||
StartSlot, NumViews, ppShaderResourceViews);
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::HSGetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState** ppSamplers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetSamplers<DxbcProgramType::HullShader>(
|
||||
StartSlot, NumSamplers, ppSamplers);
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::DSSetShader(
|
||||
ID3D11DomainShader* pDomainShader,
|
||||
ID3D11ClassInstance* const* ppClassInstances,
|
||||
UINT NumClassInstances) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
auto shader = static_cast<D3D11DomainShader*>(pDomainShader);
|
||||
|
||||
if (NumClassInstances)
|
||||
Logger::err("D3D11: Class instances not supported");
|
||||
|
||||
if (m_state.ds != shader) {
|
||||
m_state.ds = shader;
|
||||
|
||||
BindShader<DxbcProgramType::DomainShader>(GetCommonShader(shader));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::DSSetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
SetConstantBuffers<DxbcProgramType::DomainShader>(
|
||||
StartSlot, NumBuffers, ppConstantBuffers);
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::DSSetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers,
|
||||
const UINT* pFirstConstant,
|
||||
const UINT* pNumConstants) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
SetConstantBuffers1<DxbcProgramType::DomainShader>(
|
||||
StartSlot, NumBuffers, ppConstantBuffers,
|
||||
pFirstConstant, pNumConstants);
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::DSSetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView* const* ppShaderResourceViews) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
SetShaderResources<DxbcProgramType::DomainShader>(
|
||||
StartSlot, NumViews, ppShaderResourceViews);
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::DSSetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState* const* ppSamplers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
SetSamplers<DxbcProgramType::DomainShader>(
|
||||
StartSlot, NumSamplers, ppSamplers);
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::DSGetShader(
|
||||
ID3D11DomainShader** ppDomainShader,
|
||||
ID3D11ClassInstance** ppClassInstances,
|
||||
UINT* pNumClassInstances) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
if (ppDomainShader != nullptr)
|
||||
*ppDomainShader = m_state.ds.shader.ref();
|
||||
|
||||
if (pNumClassInstances != nullptr)
|
||||
|
||||
if (ppDomainShader)
|
||||
*ppDomainShader = m_state.ds.ref();
|
||||
|
||||
if (pNumClassInstances)
|
||||
*pNumClassInstances = 0;
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::DSGetConstantBuffers(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::DSGetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppConstantBuffers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetConstantBuffers(
|
||||
m_state.ds.constantBuffers,
|
||||
StartSlot, NumBuffers,
|
||||
ppConstantBuffers,
|
||||
|
||||
GetConstantBuffers<DxbcProgramType::DomainShader>(
|
||||
StartSlot, NumBuffers, ppConstantBuffers,
|
||||
nullptr, nullptr);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::DSGetConstantBuffers1(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::DSGetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppConstantBuffers,
|
||||
UINT* pFirstConstant,
|
||||
UINT* pFirstConstant,
|
||||
UINT* pNumConstants) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetConstantBuffers(
|
||||
m_state.ds.constantBuffers,
|
||||
StartSlot, NumBuffers,
|
||||
ppConstantBuffers,
|
||||
pFirstConstant,
|
||||
pNumConstants);
|
||||
|
||||
GetConstantBuffers<DxbcProgramType::DomainShader>(
|
||||
StartSlot, NumBuffers, ppConstantBuffers,
|
||||
pFirstConstant, pNumConstants);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::DSGetShaderResources(
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::DSGetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView** ppShaderResourceViews) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetShaderResources(m_state.ds.shaderResources,
|
||||
|
||||
GetShaderResources<DxbcProgramType::DomainShader>(
|
||||
StartSlot, NumViews, ppShaderResourceViews);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::DSGetSamplers(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::DSGetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState** ppSamplers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetSamplers(m_state.ds.samplers,
|
||||
|
||||
GetSamplers<DxbcProgramType::DomainShader>(
|
||||
StartSlot, NumSamplers, ppSamplers);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::GSSetShader(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::GSSetShader(
|
||||
ID3D11GeometryShader* pShader,
|
||||
ID3D11ClassInstance* const* ppClassInstances,
|
||||
UINT NumClassInstances) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
auto shader = static_cast<D3D11GeometryShader*>(pShader);
|
||||
|
||||
if (NumClassInstances != 0)
|
||||
|
||||
if (NumClassInstances)
|
||||
Logger::err("D3D11: Class instances not supported");
|
||||
|
||||
if (m_state.gs.shader != shader) {
|
||||
m_state.gs.shader = shader;
|
||||
|
||||
if (m_state.gs != shader) {
|
||||
m_state.gs = shader;
|
||||
|
||||
BindShader<DxbcProgramType::GeometryShader>(GetCommonShader(shader));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::GSSetConstantBuffers(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::GSSetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
SetConstantBuffers<DxbcProgramType::GeometryShader>(
|
||||
m_state.gs.constantBuffers,
|
||||
StartSlot, NumBuffers,
|
||||
ppConstantBuffers);
|
||||
StartSlot, NumBuffers, ppConstantBuffers);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::GSSetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::GSSetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers,
|
||||
const UINT* pFirstConstant,
|
||||
const UINT* pFirstConstant,
|
||||
const UINT* pNumConstants) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
SetConstantBuffers1<DxbcProgramType::GeometryShader>(
|
||||
m_state.gs.constantBuffers,
|
||||
StartSlot, NumBuffers,
|
||||
ppConstantBuffers,
|
||||
pFirstConstant,
|
||||
pNumConstants);
|
||||
StartSlot, NumBuffers, ppConstantBuffers,
|
||||
pFirstConstant, pNumConstants);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::GSSetShaderResources(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::GSSetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView* const* ppShaderResourceViews) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
SetShaderResources<DxbcProgramType::GeometryShader>(
|
||||
m_state.gs.shaderResources,
|
||||
StartSlot, NumViews,
|
||||
ppShaderResourceViews);
|
||||
StartSlot, NumViews, ppShaderResourceViews);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::GSSetSamplers(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::GSSetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState* const* ppSamplers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
SetSamplers<DxbcProgramType::GeometryShader>(
|
||||
m_state.gs.samplers,
|
||||
StartSlot, NumSamplers,
|
||||
ppSamplers);
|
||||
StartSlot, NumSamplers, ppSamplers);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::GSGetShader(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::GSGetShader(
|
||||
ID3D11GeometryShader** ppGeometryShader,
|
||||
ID3D11ClassInstance** ppClassInstances,
|
||||
UINT* pNumClassInstances) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
if (ppGeometryShader != nullptr)
|
||||
*ppGeometryShader = m_state.gs.shader.ref();
|
||||
|
||||
if (pNumClassInstances != nullptr)
|
||||
|
||||
if (ppGeometryShader)
|
||||
*ppGeometryShader = m_state.gs.ref();
|
||||
|
||||
if (pNumClassInstances)
|
||||
*pNumClassInstances = 0;
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::GSGetConstantBuffers(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::GSGetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppConstantBuffers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetConstantBuffers(
|
||||
m_state.gs.constantBuffers,
|
||||
StartSlot, NumBuffers,
|
||||
ppConstantBuffers,
|
||||
|
||||
GetConstantBuffers<DxbcProgramType::GeometryShader>(
|
||||
StartSlot, NumBuffers, ppConstantBuffers,
|
||||
nullptr, nullptr);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::GSGetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppConstantBuffers,
|
||||
UINT* pFirstConstant,
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::GSGetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppConstantBuffers,
|
||||
UINT* pFirstConstant,
|
||||
UINT* pNumConstants) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetConstantBuffers(
|
||||
m_state.gs.constantBuffers,
|
||||
StartSlot, NumBuffers,
|
||||
ppConstantBuffers,
|
||||
pFirstConstant,
|
||||
pNumConstants);
|
||||
|
||||
GetConstantBuffers<DxbcProgramType::GeometryShader>(
|
||||
StartSlot, NumBuffers, ppConstantBuffers,
|
||||
pFirstConstant, pNumConstants);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::GSGetShaderResources(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::GSGetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView** ppShaderResourceViews) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetShaderResources(m_state.gs.shaderResources,
|
||||
|
||||
GetShaderResources<DxbcProgramType::GeometryShader>(
|
||||
StartSlot, NumViews, ppShaderResourceViews);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::GSGetSamplers(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::GSGetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState** ppSamplers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetSamplers(m_state.gs.samplers,
|
||||
|
||||
GetSamplers<DxbcProgramType::GeometryShader>(
|
||||
StartSlot, NumSamplers, ppSamplers);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::PSSetShader(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::PSSetShader(
|
||||
ID3D11PixelShader* pPixelShader,
|
||||
ID3D11ClassInstance* const* ppClassInstances,
|
||||
UINT NumClassInstances) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
auto shader = static_cast<D3D11PixelShader*>(pPixelShader);
|
||||
|
||||
if (NumClassInstances != 0)
|
||||
|
||||
if (NumClassInstances)
|
||||
Logger::err("D3D11: Class instances not supported");
|
||||
|
||||
if (m_state.ps.shader != shader) {
|
||||
m_state.ps.shader = shader;
|
||||
|
||||
if (m_state.ps != shader) {
|
||||
m_state.ps = shader;
|
||||
|
||||
BindShader<DxbcProgramType::PixelShader>(GetCommonShader(shader));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::PSSetConstantBuffers(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::PSSetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
SetConstantBuffers<DxbcProgramType::PixelShader>(
|
||||
m_state.ps.constantBuffers,
|
||||
StartSlot, NumBuffers,
|
||||
ppConstantBuffers);
|
||||
StartSlot, NumBuffers, ppConstantBuffers);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::PSSetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers,
|
||||
const UINT* pFirstConstant,
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::PSSetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers,
|
||||
const UINT* pFirstConstant,
|
||||
const UINT* pNumConstants) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
SetConstantBuffers1<DxbcProgramType::PixelShader>(
|
||||
m_state.ps.constantBuffers,
|
||||
StartSlot, NumBuffers,
|
||||
ppConstantBuffers,
|
||||
pFirstConstant,
|
||||
pNumConstants);
|
||||
StartSlot, NumBuffers, ppConstantBuffers,
|
||||
pFirstConstant, pNumConstants);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::PSSetShaderResources(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::PSSetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView* const* ppShaderResourceViews) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
SetShaderResources<DxbcProgramType::PixelShader>(
|
||||
m_state.ps.shaderResources,
|
||||
StartSlot, NumViews,
|
||||
ppShaderResourceViews);
|
||||
StartSlot, NumViews, ppShaderResourceViews);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::PSSetSamplers(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::PSSetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState* const* ppSamplers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
SetSamplers<DxbcProgramType::PixelShader>(
|
||||
m_state.ps.samplers,
|
||||
StartSlot, NumSamplers,
|
||||
ppSamplers);
|
||||
StartSlot, NumSamplers, ppSamplers);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::PSGetShader(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::PSGetShader(
|
||||
ID3D11PixelShader** ppPixelShader,
|
||||
ID3D11ClassInstance** ppClassInstances,
|
||||
UINT* pNumClassInstances) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
if (ppPixelShader != nullptr)
|
||||
*ppPixelShader = m_state.ps.shader.ref();
|
||||
|
||||
if (pNumClassInstances != nullptr)
|
||||
|
||||
if (ppPixelShader)
|
||||
*ppPixelShader = m_state.ps.ref();
|
||||
|
||||
if (pNumClassInstances)
|
||||
*pNumClassInstances = 0;
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::PSGetConstantBuffers(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::PSGetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppConstantBuffers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetConstantBuffers(
|
||||
m_state.ps.constantBuffers,
|
||||
StartSlot, NumBuffers,
|
||||
ppConstantBuffers,
|
||||
|
||||
GetConstantBuffers<DxbcProgramType::PixelShader>(
|
||||
StartSlot, NumBuffers, ppConstantBuffers,
|
||||
nullptr, nullptr);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::PSGetConstantBuffers1(
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::PSGetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppConstantBuffers,
|
||||
UINT* pFirstConstant,
|
||||
UINT* pFirstConstant,
|
||||
UINT* pNumConstants) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetConstantBuffers(
|
||||
m_state.ps.constantBuffers,
|
||||
StartSlot, NumBuffers,
|
||||
ppConstantBuffers,
|
||||
pFirstConstant,
|
||||
pNumConstants);
|
||||
|
||||
GetConstantBuffers<DxbcProgramType::PixelShader>(
|
||||
StartSlot, NumBuffers, ppConstantBuffers,
|
||||
pFirstConstant, pNumConstants);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::PSGetShaderResources(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::PSGetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView** ppShaderResourceViews) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetShaderResources(m_state.ps.shaderResources,
|
||||
|
||||
GetShaderResources<DxbcProgramType::PixelShader>(
|
||||
StartSlot, NumViews, ppShaderResourceViews);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::PSGetSamplers(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::PSGetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState** ppSamplers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetSamplers(m_state.ps.samplers,
|
||||
|
||||
GetSamplers<DxbcProgramType::PixelShader>(
|
||||
StartSlot, NumSamplers, ppSamplers);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::CSSetShader(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::CSSetShader(
|
||||
ID3D11ComputeShader* pComputeShader,
|
||||
ID3D11ClassInstance* const* ppClassInstances,
|
||||
UINT NumClassInstances) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
auto shader = static_cast<D3D11ComputeShader*>(pComputeShader);
|
||||
|
||||
if (NumClassInstances != 0)
|
||||
|
||||
if (NumClassInstances)
|
||||
Logger::err("D3D11: Class instances not supported");
|
||||
|
||||
if (m_state.cs.shader != shader) {
|
||||
m_state.cs.shader = shader;
|
||||
|
||||
if (m_state.cs != shader) {
|
||||
m_state.cs = shader;
|
||||
|
||||
BindShader<DxbcProgramType::ComputeShader>(GetCommonShader(shader));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::CSSetConstantBuffers(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::CSSetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
SetConstantBuffers<DxbcProgramType::ComputeShader>(
|
||||
m_state.cs.constantBuffers,
|
||||
StartSlot, NumBuffers,
|
||||
ppConstantBuffers);
|
||||
StartSlot, NumBuffers, ppConstantBuffers);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::CSSetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers,
|
||||
const UINT* pFirstConstant,
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::CSSetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers,
|
||||
const UINT* pFirstConstant,
|
||||
const UINT* pNumConstants) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
SetConstantBuffers1<DxbcProgramType::ComputeShader>(
|
||||
m_state.cs.constantBuffers,
|
||||
StartSlot, NumBuffers,
|
||||
ppConstantBuffers,
|
||||
pFirstConstant,
|
||||
pNumConstants);
|
||||
StartSlot, NumBuffers, ppConstantBuffers,
|
||||
pFirstConstant, pNumConstants);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::CSSetShaderResources(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::CSSetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView* const* ppShaderResourceViews) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
SetShaderResources<DxbcProgramType::ComputeShader>(
|
||||
m_state.cs.shaderResources,
|
||||
StartSlot, NumViews,
|
||||
ppShaderResourceViews);
|
||||
StartSlot, NumViews, ppShaderResourceViews);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::CSSetSamplers(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::CSSetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState* const* ppSamplers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
SetSamplers<DxbcProgramType::ComputeShader>(
|
||||
m_state.cs.samplers,
|
||||
StartSlot, NumSamplers,
|
||||
ppSamplers);
|
||||
StartSlot, NumSamplers, ppSamplers);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::CSSetUnorderedAccessViews(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::CSSetUnorderedAccessViews(
|
||||
UINT StartSlot,
|
||||
UINT NumUAVs,
|
||||
ID3D11UnorderedAccessView* const* ppUnorderedAccessViews,
|
||||
@ -2266,31 +2065,31 @@ namespace dxvk {
|
||||
|
||||
if (TestRtvUavHazards(0, nullptr, NumUAVs, ppUnorderedAccessViews))
|
||||
return;
|
||||
|
||||
|
||||
// Unbind previously bound conflicting UAVs
|
||||
uint32_t uavSlotId = computeUavBinding (DxbcProgramType::ComputeShader, 0);
|
||||
uint32_t ctrSlotId = computeUavCounterBinding(DxbcProgramType::ComputeShader, 0);
|
||||
|
||||
int32_t uavId = m_state.cs.uavMask.findNext(0);
|
||||
int32_t uavId = m_state.uav.mask.findNext(0);
|
||||
|
||||
while (uavId >= 0) {
|
||||
if (uint32_t(uavId) < StartSlot || uint32_t(uavId) >= StartSlot + NumUAVs) {
|
||||
for (uint32_t i = 0; i < NumUAVs; i++) {
|
||||
auto uav = static_cast<D3D11UnorderedAccessView*>(ppUnorderedAccessViews[i]);
|
||||
|
||||
if (CheckViewOverlap(uav, m_state.cs.unorderedAccessViews[uavId].ptr())) {
|
||||
m_state.cs.unorderedAccessViews[uavId] = nullptr;
|
||||
m_state.cs.uavMask.clr(uavId);
|
||||
if (CheckViewOverlap(uav, m_state.uav.views[uavId].ptr())) {
|
||||
m_state.uav.views[uavId] = nullptr;
|
||||
m_state.uav.mask.clr(uavId);
|
||||
|
||||
BindUnorderedAccessView(
|
||||
BindUnorderedAccessView<DxbcProgramType::ComputeShader>(
|
||||
uavSlotId + uavId, nullptr,
|
||||
ctrSlotId + uavId, ~0u);
|
||||
}
|
||||
}
|
||||
|
||||
uavId = m_state.cs.uavMask.findNext(uavId + 1);
|
||||
uavId = m_state.uav.mask.findNext(uavId + 1);
|
||||
} else {
|
||||
uavId = m_state.cs.uavMask.findNext(StartSlot + NumUAVs);
|
||||
uavId = m_state.uav.mask.findNext(StartSlot + NumUAVs);
|
||||
}
|
||||
}
|
||||
|
||||
@ -2299,112 +2098,120 @@ namespace dxvk {
|
||||
auto uav = static_cast<D3D11UnorderedAccessView*>(ppUnorderedAccessViews[i]);
|
||||
auto ctr = pUAVInitialCounts ? pUAVInitialCounts[i] : ~0u;
|
||||
|
||||
if (m_state.cs.unorderedAccessViews[StartSlot + i] != uav || ctr != ~0u) {
|
||||
m_state.cs.unorderedAccessViews[StartSlot + i] = uav;
|
||||
m_state.cs.uavMask.set(StartSlot + i, uav != nullptr);
|
||||
if (m_state.uav.views[StartSlot + i] != uav || ctr != ~0u) {
|
||||
m_state.uav.views[StartSlot + i] = uav;
|
||||
m_state.uav.mask.set(StartSlot + i, uav != nullptr);
|
||||
|
||||
BindUnorderedAccessView(
|
||||
BindUnorderedAccessView<DxbcProgramType::ComputeShader>(
|
||||
uavSlotId + StartSlot + i, uav,
|
||||
ctrSlotId + StartSlot + i, ctr);
|
||||
|
||||
|
||||
ResolveCsSrvHazards(uav);
|
||||
}
|
||||
}
|
||||
|
||||
m_state.uav.maxCount = std::clamp(StartSlot + NumUAVs,
|
||||
m_state.uav.maxCount, uint32_t(m_state.uav.views.size()));
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::CSGetShader(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::CSGetShader(
|
||||
ID3D11ComputeShader** ppComputeShader,
|
||||
ID3D11ClassInstance** ppClassInstances,
|
||||
UINT* pNumClassInstances) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
if (ppComputeShader != nullptr)
|
||||
*ppComputeShader = m_state.cs.shader.ref();
|
||||
|
||||
if (pNumClassInstances != nullptr)
|
||||
|
||||
if (ppComputeShader)
|
||||
*ppComputeShader = m_state.cs.ref();
|
||||
|
||||
if (pNumClassInstances)
|
||||
*pNumClassInstances = 0;
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::CSGetConstantBuffers(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::CSGetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppConstantBuffers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetConstantBuffers(
|
||||
m_state.cs.constantBuffers,
|
||||
StartSlot, NumBuffers,
|
||||
ppConstantBuffers,
|
||||
|
||||
GetConstantBuffers<DxbcProgramType::ComputeShader>(
|
||||
StartSlot, NumBuffers, ppConstantBuffers,
|
||||
nullptr, nullptr);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::CSGetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::CSGetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppConstantBuffers,
|
||||
UINT* pFirstConstant,
|
||||
ID3D11Buffer** ppConstantBuffers,
|
||||
UINT* pFirstConstant,
|
||||
UINT* pNumConstants) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetConstantBuffers(
|
||||
m_state.cs.constantBuffers,
|
||||
StartSlot, NumBuffers,
|
||||
ppConstantBuffers,
|
||||
pFirstConstant,
|
||||
pNumConstants);
|
||||
|
||||
GetConstantBuffers<DxbcProgramType::ComputeShader>(
|
||||
StartSlot, NumBuffers, ppConstantBuffers,
|
||||
pFirstConstant, pNumConstants);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::CSGetShaderResources(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::CSGetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView** ppShaderResourceViews) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetShaderResources(m_state.cs.shaderResources,
|
||||
|
||||
GetShaderResources<DxbcProgramType::ComputeShader>(
|
||||
StartSlot, NumViews, ppShaderResourceViews);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::CSGetSamplers(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::CSGetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState** ppSamplers) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
GetSamplers(m_state.cs.samplers,
|
||||
|
||||
GetSamplers<DxbcProgramType::ComputeShader>(
|
||||
StartSlot, NumSamplers, ppSamplers);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::CSGetUnorderedAccessViews(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::CSGetUnorderedAccessViews(
|
||||
UINT StartSlot,
|
||||
UINT NumUAVs,
|
||||
ID3D11UnorderedAccessView** ppUnorderedAccessViews) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
for (uint32_t i = 0; i < NumUAVs; i++) {
|
||||
ppUnorderedAccessViews[i] = StartSlot + i < m_state.cs.unorderedAccessViews.size()
|
||||
? m_state.cs.unorderedAccessViews[StartSlot + i].ref()
|
||||
ppUnorderedAccessViews[i] = StartSlot + i < m_state.uav.views.size()
|
||||
? m_state.uav.views[StartSlot + i].ref()
|
||||
: nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::OMSetRenderTargets(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::OMSetRenderTargets(
|
||||
UINT NumViews,
|
||||
ID3D11RenderTargetView* const* ppRenderTargetViews,
|
||||
ID3D11DepthStencilView* pDepthStencilView) {
|
||||
OMSetRenderTargetsAndUnorderedAccessViews(
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
SetRenderTargetsAndUnorderedAccessViews(
|
||||
NumViews, ppRenderTargetViews, pDepthStencilView,
|
||||
NumViews, 0, nullptr, nullptr);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::OMSetRenderTargetsAndUnorderedAccessViews(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::OMSetRenderTargetsAndUnorderedAccessViews(
|
||||
UINT NumRTVs,
|
||||
ID3D11RenderTargetView* const* ppRenderTargetViews,
|
||||
ID3D11DepthStencilView* pDepthStencilView,
|
||||
@ -2414,233 +2221,177 @@ namespace dxvk {
|
||||
const UINT* pUAVInitialCounts) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
if (TestRtvUavHazards(NumRTVs, ppRenderTargetViews, NumUAVs, ppUnorderedAccessViews))
|
||||
return;
|
||||
|
||||
bool needsUpdate = false;
|
||||
|
||||
if (likely(NumRTVs != D3D11_KEEP_RENDER_TARGETS_AND_DEPTH_STENCIL)) {
|
||||
// Native D3D11 does not change the render targets if
|
||||
// the parameters passed to this method are invalid.
|
||||
if (!ValidateRenderTargets(NumRTVs, ppRenderTargetViews, pDepthStencilView))
|
||||
return;
|
||||
|
||||
for (uint32_t i = 0; i < m_state.om.renderTargetViews.size(); i++) {
|
||||
auto rtv = i < NumRTVs
|
||||
? static_cast<D3D11RenderTargetView*>(ppRenderTargetViews[i])
|
||||
: nullptr;
|
||||
|
||||
if (m_state.om.renderTargetViews[i] != rtv) {
|
||||
m_state.om.renderTargetViews[i] = rtv;
|
||||
needsUpdate = true;
|
||||
ResolveOmSrvHazards(rtv);
|
||||
|
||||
if (NumUAVs == D3D11_KEEP_UNORDERED_ACCESS_VIEWS)
|
||||
ResolveOmUavHazards(rtv);
|
||||
}
|
||||
}
|
||||
|
||||
auto dsv = static_cast<D3D11DepthStencilView*>(pDepthStencilView);
|
||||
|
||||
if (m_state.om.depthStencilView != dsv) {
|
||||
m_state.om.depthStencilView = dsv;
|
||||
needsUpdate = true;
|
||||
ResolveOmSrvHazards(dsv);
|
||||
}
|
||||
|
||||
m_state.om.maxRtv = NumRTVs;
|
||||
}
|
||||
|
||||
if (unlikely(NumUAVs || m_state.om.maxUav)) {
|
||||
uint32_t uavSlotId = computeUavBinding (DxbcProgramType::PixelShader, 0);
|
||||
uint32_t ctrSlotId = computeUavCounterBinding(DxbcProgramType::PixelShader, 0);
|
||||
|
||||
if (likely(NumUAVs != D3D11_KEEP_UNORDERED_ACCESS_VIEWS)) {
|
||||
uint32_t newMaxUav = NumUAVs ? UAVStartSlot + NumUAVs : 0;
|
||||
uint32_t oldMaxUav = std::exchange(m_state.om.maxUav, newMaxUav);
|
||||
|
||||
for (uint32_t i = 0; i < std::max(oldMaxUav, newMaxUav); i++) {
|
||||
D3D11UnorderedAccessView* uav = nullptr;
|
||||
uint32_t ctr = ~0u;
|
||||
|
||||
if (i >= UAVStartSlot && i < UAVStartSlot + NumUAVs) {
|
||||
uav = static_cast<D3D11UnorderedAccessView*>(ppUnorderedAccessViews[i - UAVStartSlot]);
|
||||
ctr = pUAVInitialCounts ? pUAVInitialCounts[i - UAVStartSlot] : ~0u;
|
||||
}
|
||||
|
||||
if (m_state.ps.unorderedAccessViews[i] != uav || ctr != ~0u) {
|
||||
m_state.ps.unorderedAccessViews[i] = uav;
|
||||
|
||||
BindUnorderedAccessView(
|
||||
uavSlotId + i, uav,
|
||||
ctrSlotId + i, ctr);
|
||||
|
||||
ResolveOmSrvHazards(uav);
|
||||
|
||||
if (NumRTVs == D3D11_KEEP_RENDER_TARGETS_AND_DEPTH_STENCIL)
|
||||
needsUpdate |= ResolveOmRtvHazards(uav);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (needsUpdate)
|
||||
BindFramebuffer();
|
||||
SetRenderTargetsAndUnorderedAccessViews(
|
||||
NumRTVs, ppRenderTargetViews, pDepthStencilView,
|
||||
UAVStartSlot, NumUAVs, ppUnorderedAccessViews, pUAVInitialCounts);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::OMSetBlendState(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::OMSetBlendState(
|
||||
ID3D11BlendState* pBlendState,
|
||||
const FLOAT BlendFactor[4],
|
||||
UINT SampleMask) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
auto blendState = static_cast<D3D11BlendState*>(pBlendState);
|
||||
|
||||
|
||||
if (m_state.om.cbState != blendState
|
||||
|| m_state.om.sampleMask != SampleMask) {
|
||||
m_state.om.cbState = blendState;
|
||||
m_state.om.sampleMask = SampleMask;
|
||||
|
||||
|
||||
ApplyBlendState();
|
||||
}
|
||||
|
||||
|
||||
if (BlendFactor != nullptr) {
|
||||
for (uint32_t i = 0; i < 4; i++)
|
||||
m_state.om.blendFactor[i] = BlendFactor[i];
|
||||
|
||||
|
||||
ApplyBlendFactor();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::OMSetDepthStencilState(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::OMSetDepthStencilState(
|
||||
ID3D11DepthStencilState* pDepthStencilState,
|
||||
UINT StencilRef) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
auto depthStencilState = static_cast<D3D11DepthStencilState*>(pDepthStencilState);
|
||||
|
||||
|
||||
if (m_state.om.dsState != depthStencilState) {
|
||||
m_state.om.dsState = depthStencilState;
|
||||
ApplyDepthStencilState();
|
||||
}
|
||||
|
||||
|
||||
// The D3D11 runtime only appears to store the low 8 bits,
|
||||
// and some games rely on this behaviour. Do the same here.
|
||||
StencilRef &= 0xFF;
|
||||
|
||||
if (m_state.om.stencilRef != StencilRef) {
|
||||
m_state.om.stencilRef = StencilRef;
|
||||
ApplyStencilRef();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::OMGetRenderTargets(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::OMGetRenderTargets(
|
||||
UINT NumViews,
|
||||
ID3D11RenderTargetView** ppRenderTargetViews,
|
||||
ID3D11DepthStencilView** ppDepthStencilView) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
if (ppRenderTargetViews != nullptr) {
|
||||
for (UINT i = 0; i < NumViews; i++) {
|
||||
ppRenderTargetViews[i] = i < m_state.om.renderTargetViews.size()
|
||||
? m_state.om.renderTargetViews[i].ref()
|
||||
: nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
if (ppDepthStencilView != nullptr)
|
||||
*ppDepthStencilView = m_state.om.depthStencilView.ref();
|
||||
OMGetRenderTargetsAndUnorderedAccessViews(
|
||||
NumViews, ppRenderTargetViews, ppDepthStencilView,
|
||||
NumViews, 0, nullptr);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::OMGetRenderTargetsAndUnorderedAccessViews(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::OMGetRenderTargetsAndUnorderedAccessViews(
|
||||
UINT NumRTVs,
|
||||
ID3D11RenderTargetView** ppRenderTargetViews,
|
||||
ID3D11DepthStencilView** ppDepthStencilView,
|
||||
UINT UAVStartSlot,
|
||||
UINT NumUAVs,
|
||||
ID3D11UnorderedAccessView** ppUnorderedAccessViews) {
|
||||
OMGetRenderTargets(NumRTVs, ppRenderTargetViews, ppDepthStencilView);
|
||||
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
if (ppUnorderedAccessViews != nullptr) {
|
||||
|
||||
if (ppRenderTargetViews) {
|
||||
for (UINT i = 0; i < NumRTVs; i++) {
|
||||
ppRenderTargetViews[i] = i < m_state.om.rtvs.size()
|
||||
? m_state.om.rtvs[i].ref()
|
||||
: nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
if (ppDepthStencilView)
|
||||
*ppDepthStencilView = m_state.om.dsv.ref();
|
||||
|
||||
if (ppUnorderedAccessViews) {
|
||||
for (UINT i = 0; i < NumUAVs; i++) {
|
||||
ppUnorderedAccessViews[i] = UAVStartSlot + i < m_state.ps.unorderedAccessViews.size()
|
||||
? m_state.ps.unorderedAccessViews[UAVStartSlot + i].ref()
|
||||
ppUnorderedAccessViews[i] = UAVStartSlot + i < m_state.om.uavs.size()
|
||||
? m_state.om.uavs[UAVStartSlot + i].ref()
|
||||
: nullptr;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::OMGetBlendState(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::OMGetBlendState(
|
||||
ID3D11BlendState** ppBlendState,
|
||||
FLOAT BlendFactor[4],
|
||||
UINT* pSampleMask) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
if (ppBlendState != nullptr)
|
||||
|
||||
if (ppBlendState)
|
||||
*ppBlendState = ref(m_state.om.cbState);
|
||||
|
||||
if (BlendFactor != nullptr)
|
||||
|
||||
if (BlendFactor)
|
||||
std::memcpy(BlendFactor, m_state.om.blendFactor, sizeof(FLOAT) * 4);
|
||||
|
||||
if (pSampleMask != nullptr)
|
||||
|
||||
if (pSampleMask)
|
||||
*pSampleMask = m_state.om.sampleMask;
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::OMGetDepthStencilState(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::OMGetDepthStencilState(
|
||||
ID3D11DepthStencilState** ppDepthStencilState,
|
||||
UINT* pStencilRef) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
if (ppDepthStencilState != nullptr)
|
||||
|
||||
if (ppDepthStencilState)
|
||||
*ppDepthStencilState = ref(m_state.om.dsState);
|
||||
|
||||
if (pStencilRef != nullptr)
|
||||
|
||||
if (pStencilRef)
|
||||
*pStencilRef = m_state.om.stencilRef;
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::RSSetState(ID3D11RasterizerState* pRasterizerState) {
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::RSSetState(ID3D11RasterizerState* pRasterizerState) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
auto rasterizerState = static_cast<D3D11RasterizerState*>(pRasterizerState);
|
||||
|
||||
bool currScissorEnable = m_state.rs.state != nullptr
|
||||
? m_state.rs.state->Desc()->ScissorEnable
|
||||
: false;
|
||||
|
||||
bool nextScissorEnable = rasterizerState != nullptr
|
||||
? rasterizerState->Desc()->ScissorEnable
|
||||
: false;
|
||||
|
||||
if (m_state.rs.state != rasterizerState) {
|
||||
m_state.rs.state = rasterizerState;
|
||||
auto currRasterizerState = m_state.rs.state;
|
||||
auto nextRasterizerState = static_cast<D3D11RasterizerState*>(pRasterizerState);
|
||||
|
||||
// In D3D11, the rasterizer state defines whether the
|
||||
// scissor test is enabled, so we have to update the
|
||||
// scissor rectangles as well.
|
||||
if (m_state.rs.state != nextRasterizerState) {
|
||||
m_state.rs.state = nextRasterizerState;
|
||||
ApplyRasterizerState();
|
||||
|
||||
// If necessary, update the rasterizer sample count push constant
|
||||
uint32_t currSampleCount = currRasterizerState != nullptr ? currRasterizerState->Desc()->ForcedSampleCount : 0;
|
||||
uint32_t nextSampleCount = nextRasterizerState != nullptr ? nextRasterizerState->Desc()->ForcedSampleCount : 0;
|
||||
|
||||
if (currSampleCount != nextSampleCount)
|
||||
ApplyRasterizerSampleCount();
|
||||
|
||||
// In D3D11, the rasterizer state defines whether the scissor test is
|
||||
// enabled, so if that changes, we need to update scissor rects as well.
|
||||
bool currScissorEnable = currRasterizerState != nullptr ? currRasterizerState->Desc()->ScissorEnable : false;
|
||||
bool nextScissorEnable = nextRasterizerState != nullptr ? nextRasterizerState->Desc()->ScissorEnable : false;
|
||||
|
||||
if (currScissorEnable != nextScissorEnable)
|
||||
ApplyViewportState();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::RSSetViewports(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::RSSetViewports(
|
||||
UINT NumViewports,
|
||||
const D3D11_VIEWPORT* pViewports) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
if (unlikely(NumViewports > m_state.rs.viewports.size()))
|
||||
return;
|
||||
|
||||
|
||||
bool dirty = m_state.rs.numViewports != NumViewports;
|
||||
m_state.rs.numViewports = NumViewports;
|
||||
|
||||
|
||||
for (uint32_t i = 0; i < NumViewports; i++) {
|
||||
const D3D11_VIEWPORT& vp = m_state.rs.viewports[i];
|
||||
|
||||
@ -2653,23 +2404,24 @@ namespace dxvk {
|
||||
|
||||
m_state.rs.viewports[i] = pViewports[i];
|
||||
}
|
||||
|
||||
|
||||
if (dirty)
|
||||
ApplyViewportState();
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::RSSetScissorRects(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::RSSetScissorRects(
|
||||
UINT NumRects,
|
||||
const D3D11_RECT* pRects) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
if (unlikely(NumRects > m_state.rs.scissors.size()))
|
||||
return;
|
||||
|
||||
|
||||
bool dirty = m_state.rs.numScissors != NumRects;
|
||||
m_state.rs.numScissors = NumRects;
|
||||
|
||||
|
||||
for (uint32_t i = 0; i < NumRects; i++) {
|
||||
if (pRects[i].bottom >= pRects[i].top
|
||||
&& pRects[i].right >= pRects[i].left) {
|
||||
@ -2687,22 +2439,24 @@ namespace dxvk {
|
||||
if (m_state.rs.state != nullptr && dirty) {
|
||||
D3D11_RASTERIZER_DESC rsDesc;
|
||||
m_state.rs.state->GetDesc(&rsDesc);
|
||||
|
||||
|
||||
if (rsDesc.ScissorEnable)
|
||||
ApplyViewportState();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::RSGetState(ID3D11RasterizerState** ppRasterizerState) {
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::RSGetState(ID3D11RasterizerState** ppRasterizerState) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
if (ppRasterizerState != nullptr)
|
||||
|
||||
if (ppRasterizerState)
|
||||
*ppRasterizerState = ref(m_state.rs.state);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::RSGetViewports(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::RSGetViewports(
|
||||
UINT* pNumViewports,
|
||||
D3D11_VIEWPORT* pViewports) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
@ -2727,14 +2481,15 @@ namespace dxvk {
|
||||
|
||||
*pNumViewports = numWritten;
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::RSGetScissorRects(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::RSGetScissorRects(
|
||||
UINT* pNumRects,
|
||||
D3D11_RECT* pRects) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
uint32_t numWritten = m_state.rs.numScissors;
|
||||
|
||||
|
||||
if (pRects) {
|
||||
numWritten = std::min(numWritten, *pNumRects);
|
||||
|
||||
@ -2754,12 +2509,13 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::SOSetTargets(
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::SOSetTargets(
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppSOTargets,
|
||||
const UINT* pOffsets) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
for (uint32_t i = 0; i < NumBuffers; i++) {
|
||||
D3D11Buffer* buffer = static_cast<D3D11Buffer*>(ppSOTargets[i]);
|
||||
UINT offset = pOffsets != nullptr ? pOffsets[i] : 0;
|
||||
@ -2779,37 +2535,39 @@ namespace dxvk {
|
||||
m_state.so.targets[i].offset);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::SOGetTargets(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::SOGetTargets(
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppSOTargets) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
for (uint32_t i = 0; i < NumBuffers; i++) {
|
||||
ppSOTargets[i] = i < m_state.so.targets.size()
|
||||
? m_state.so.targets[i].buffer.ref()
|
||||
: nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::SOGetTargetsWithOffsets(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::SOGetTargetsWithOffsets(
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppSOTargets,
|
||||
UINT* pOffsets) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
for (uint32_t i = 0; i < NumBuffers; i++) {
|
||||
const bool inRange = i < m_state.so.targets.size();
|
||||
|
||||
if (ppSOTargets != nullptr) {
|
||||
if (ppSOTargets) {
|
||||
ppSOTargets[i] = inRange
|
||||
? m_state.so.targets[i].buffer.ref()
|
||||
: nullptr;
|
||||
}
|
||||
|
||||
if (pOffsets != nullptr) {
|
||||
if (pOffsets) {
|
||||
pOffsets[i] = inRange
|
||||
? m_state.so.targets[i].offset
|
||||
: 0u;
|
||||
@ -2818,43 +2576,458 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
BOOL STDMETHODCALLTYPE D3D11DeviceContext::IsAnnotationEnabled() {
|
||||
return m_device->instance()->extensions().extDebugUtils;
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::SetPredication(
|
||||
ID3D11Predicate* pPredicate,
|
||||
BOOL PredicateValue) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
auto predicate = D3D11Query::FromPredicate(pPredicate);
|
||||
m_state.pr.predicateObject = predicate;
|
||||
m_state.pr.predicateValue = PredicateValue;
|
||||
|
||||
static bool s_errorShown = false;
|
||||
|
||||
if (pPredicate && !std::exchange(s_errorShown, true))
|
||||
Logger::err("D3D11DeviceContext::SetPredication: Stub");
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::SetMarkerInt(
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::GetPredication(
|
||||
ID3D11Predicate** ppPredicate,
|
||||
BOOL* pPredicateValue) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
if (ppPredicate)
|
||||
*ppPredicate = D3D11Query::AsPredicate(m_state.pr.predicateObject.ref());
|
||||
|
||||
if (pPredicateValue)
|
||||
*pPredicateValue = m_state.pr.predicateValue;
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::SetResourceMinLOD(
|
||||
ID3D11Resource* pResource,
|
||||
FLOAT MinLOD) {
|
||||
bool s_errorShown = false;
|
||||
|
||||
if (std::exchange(s_errorShown, true))
|
||||
Logger::err("D3D11DeviceContext::SetResourceMinLOD: Not implemented");
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
FLOAT STDMETHODCALLTYPE D3D11CommonContext<ContextType>::GetResourceMinLOD(ID3D11Resource* pResource) {
|
||||
bool s_errorShown = false;
|
||||
|
||||
if (std::exchange(s_errorShown, true))
|
||||
Logger::err("D3D11DeviceContext::GetResourceMinLOD: Not implemented");
|
||||
|
||||
return 0.0f;
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::CopyTiles(
|
||||
ID3D11Resource* pTiledResource,
|
||||
const D3D11_TILED_RESOURCE_COORDINATE* pTileRegionStartCoordinate,
|
||||
const D3D11_TILE_REGION_SIZE* pTileRegionSize,
|
||||
ID3D11Buffer* pBuffer,
|
||||
UINT64 BufferStartOffsetInBytes,
|
||||
UINT Flags) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
if (!pTiledResource || !pBuffer)
|
||||
return;
|
||||
|
||||
auto buffer = static_cast<D3D11Buffer*>(pBuffer);
|
||||
|
||||
// Get buffer slice and just forward the call
|
||||
VkDeviceSize bufferSize = pTileRegionSize->NumTiles * SparseMemoryPageSize;
|
||||
|
||||
if (buffer->Desc()->ByteWidth < BufferStartOffsetInBytes + bufferSize)
|
||||
return;
|
||||
|
||||
DxvkBufferSlice slice = buffer->GetBufferSlice(BufferStartOffsetInBytes, bufferSize);
|
||||
|
||||
CopyTiledResourceData(pTiledResource,
|
||||
pTileRegionStartCoordinate,
|
||||
pTileRegionSize, slice, Flags);
|
||||
|
||||
if (buffer->HasSequenceNumber())
|
||||
GetTypedContext()->TrackBufferSequenceNumber(buffer);
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
HRESULT STDMETHODCALLTYPE D3D11CommonContext<ContextType>::CopyTileMappings(
|
||||
ID3D11Resource* pDestTiledResource,
|
||||
const D3D11_TILED_RESOURCE_COORDINATE* pDestRegionCoordinate,
|
||||
ID3D11Resource* pSourceTiledResource,
|
||||
const D3D11_TILED_RESOURCE_COORDINATE* pSourceRegionCoordinate,
|
||||
const D3D11_TILE_REGION_SIZE* pTileRegionSize,
|
||||
UINT Flags) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
if (!pDestTiledResource || !pSourceTiledResource)
|
||||
return E_INVALIDARG;
|
||||
|
||||
if constexpr (!IsDeferred)
|
||||
GetTypedContext()->ConsiderFlush(GpuFlushType::ImplicitWeakHint);
|
||||
|
||||
DxvkSparseBindInfo bindInfo;
|
||||
bindInfo.dstResource = GetPagedResource(pDestTiledResource);
|
||||
bindInfo.srcResource = GetPagedResource(pSourceTiledResource);
|
||||
|
||||
auto dstPageTable = bindInfo.dstResource->getSparsePageTable();
|
||||
auto srcPageTable = bindInfo.srcResource->getSparsePageTable();
|
||||
|
||||
if (!dstPageTable || !srcPageTable)
|
||||
return E_INVALIDARG;
|
||||
|
||||
if (pDestRegionCoordinate->Subresource >= dstPageTable->getSubresourceCount()
|
||||
|| pSourceRegionCoordinate->Subresource >= srcPageTable->getSubresourceCount())
|
||||
return E_INVALIDARG;
|
||||
|
||||
VkOffset3D dstRegionOffset = {
|
||||
int32_t(pDestRegionCoordinate->X),
|
||||
int32_t(pDestRegionCoordinate->Y),
|
||||
int32_t(pDestRegionCoordinate->Z) };
|
||||
|
||||
VkOffset3D srcRegionOffset = {
|
||||
int32_t(pSourceRegionCoordinate->X),
|
||||
int32_t(pSourceRegionCoordinate->Y),
|
||||
int32_t(pSourceRegionCoordinate->Z) };
|
||||
|
||||
VkExtent3D regionExtent = {
|
||||
uint32_t(pTileRegionSize->Width),
|
||||
uint32_t(pTileRegionSize->Height),
|
||||
uint32_t(pTileRegionSize->Depth) };
|
||||
|
||||
for (uint32_t i = 0; i < pTileRegionSize->NumTiles; i++) {
|
||||
// We don't know the current tile mappings of either resource since
|
||||
// this may be called on a deferred context and tile mappings are
|
||||
// updated on the CS thread, so just resolve the copy in the backend
|
||||
uint32_t dstTile = dstPageTable->computePageIndex(
|
||||
pDestRegionCoordinate->Subresource, dstRegionOffset,
|
||||
regionExtent, !pTileRegionSize->bUseBox, i);
|
||||
|
||||
uint32_t srcTile = srcPageTable->computePageIndex(
|
||||
pSourceRegionCoordinate->Subresource, srcRegionOffset,
|
||||
regionExtent, !pTileRegionSize->bUseBox, i);
|
||||
|
||||
if (dstTile >= dstPageTable->getPageCount()
|
||||
|| srcTile >= srcPageTable->getPageCount())
|
||||
return E_INVALIDARG;
|
||||
|
||||
DxvkSparseBind bind;
|
||||
bind.mode = DxvkSparseBindMode::Copy;
|
||||
bind.dstPage = dstTile;
|
||||
bind.srcPage = srcTile;
|
||||
|
||||
bindInfo.binds.push_back(bind);
|
||||
}
|
||||
|
||||
DxvkSparseBindFlags flags = (Flags & D3D11_TILE_MAPPING_NO_OVERWRITE)
|
||||
? DxvkSparseBindFlags(DxvkSparseBindFlag::SkipSynchronization)
|
||||
: DxvkSparseBindFlags();
|
||||
|
||||
EmitCs([
|
||||
cBindInfo = std::move(bindInfo),
|
||||
cFlags = flags
|
||||
] (DxvkContext* ctx) {
|
||||
ctx->updatePageTable(cBindInfo, cFlags);
|
||||
});
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
HRESULT STDMETHODCALLTYPE D3D11CommonContext<ContextType>::ResizeTilePool(
|
||||
ID3D11Buffer* pTilePool,
|
||||
UINT64 NewSizeInBytes) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
if (NewSizeInBytes % SparseMemoryPageSize)
|
||||
return E_INVALIDARG;
|
||||
|
||||
auto buffer = static_cast<D3D11Buffer*>(pTilePool);
|
||||
|
||||
if (!buffer->IsTilePool())
|
||||
return E_INVALIDARG;
|
||||
|
||||
// Perform the resize operation. This is somewhat trivialized
|
||||
// since all lifetime tracking is done by the backend.
|
||||
EmitCs([
|
||||
cAllocator = buffer->GetSparseAllocator(),
|
||||
cPageCount = NewSizeInBytes / SparseMemoryPageSize
|
||||
] (DxvkContext* ctx) {
|
||||
cAllocator->setCapacity(cPageCount);
|
||||
});
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::TiledResourceBarrier(
|
||||
ID3D11DeviceChild* pTiledResourceOrViewAccessBeforeBarrier,
|
||||
ID3D11DeviceChild* pTiledResourceOrViewAccessAfterBarrier) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
DxvkGlobalPipelineBarrier srcBarrier = GetTiledResourceDependency(pTiledResourceOrViewAccessBeforeBarrier);
|
||||
DxvkGlobalPipelineBarrier dstBarrier = GetTiledResourceDependency(pTiledResourceOrViewAccessAfterBarrier);
|
||||
|
||||
if (srcBarrier.stages && dstBarrier.stages) {
|
||||
EmitCs([
|
||||
cSrcBarrier = srcBarrier,
|
||||
cDstBarrier = dstBarrier
|
||||
] (DxvkContext* ctx) {
|
||||
ctx->emitGraphicsBarrier(
|
||||
cSrcBarrier.stages, cSrcBarrier.access,
|
||||
cDstBarrier.stages, cDstBarrier.access);
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
HRESULT STDMETHODCALLTYPE D3D11CommonContext<ContextType>::UpdateTileMappings(
|
||||
ID3D11Resource* pTiledResource,
|
||||
UINT NumRegions,
|
||||
const D3D11_TILED_RESOURCE_COORDINATE* pRegionCoordinates,
|
||||
const D3D11_TILE_REGION_SIZE* pRegionSizes,
|
||||
ID3D11Buffer* pTilePool,
|
||||
UINT NumRanges,
|
||||
const UINT* pRangeFlags,
|
||||
const UINT* pRangeTileOffsets,
|
||||
const UINT* pRangeTileCounts,
|
||||
UINT Flags) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
if (!pTiledResource || !NumRegions || !NumRanges)
|
||||
return E_INVALIDARG;
|
||||
|
||||
if constexpr (!IsDeferred)
|
||||
GetTypedContext()->ConsiderFlush(GpuFlushType::ImplicitWeakHint);
|
||||
|
||||
// Find sparse allocator if the tile pool is defined
|
||||
DxvkSparseBindInfo bindInfo;
|
||||
|
||||
if (pTilePool) {
|
||||
auto tilePool = static_cast<D3D11Buffer*>(pTilePool);
|
||||
bindInfo.srcAllocator = tilePool->GetSparseAllocator();
|
||||
|
||||
if (bindInfo.srcAllocator == nullptr)
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
|
||||
// Find resource and sparse page table for the given resource
|
||||
bindInfo.dstResource = GetPagedResource(pTiledResource);
|
||||
auto pageTable = bindInfo.dstResource->getSparsePageTable();
|
||||
|
||||
if (!pageTable)
|
||||
return E_INVALIDARG;
|
||||
|
||||
// Lookup table in case the app tries to bind the same
|
||||
// page multiple times. We should resolve that here and
|
||||
// only consider the last bind to any given page.
|
||||
std::vector<uint32_t> bindIndices(pageTable->getPageCount(), ~0u);
|
||||
|
||||
// This function allows pretty much every parameter to be nullptr
|
||||
// in some way, so initialize some defaults as necessary
|
||||
D3D11_TILED_RESOURCE_COORDINATE regionCoord = { };
|
||||
D3D11_TILE_REGION_SIZE regionSize = { };
|
||||
|
||||
if (!pRegionSizes) {
|
||||
regionSize.NumTiles = pRegionCoordinates
|
||||
? 1 : pageTable->getPageCount();
|
||||
}
|
||||
|
||||
uint32_t rangeFlag = 0u;
|
||||
uint32_t rangeTileOffset = 0u;
|
||||
uint32_t rangeTileCount = ~0u;
|
||||
|
||||
// For now, just generate a simple list of tile index to
|
||||
// page index mappings, and let the backend optimize later
|
||||
uint32_t regionIdx = 0u;
|
||||
uint32_t regionTile = 0u;
|
||||
uint32_t rangeIdx = 0u;
|
||||
uint32_t rangeTile = 0u;
|
||||
|
||||
while (regionIdx < NumRegions && rangeIdx < NumRanges) {
|
||||
if (!regionTile) {
|
||||
if (pRegionCoordinates)
|
||||
regionCoord = pRegionCoordinates[regionIdx];
|
||||
|
||||
if (pRegionSizes)
|
||||
regionSize = pRegionSizes[regionIdx];
|
||||
}
|
||||
|
||||
if (!rangeTile) {
|
||||
if (pRangeFlags)
|
||||
rangeFlag = pRangeFlags[rangeIdx];
|
||||
|
||||
if (pRangeTileOffsets)
|
||||
rangeTileOffset = pRangeTileOffsets[rangeIdx];
|
||||
|
||||
if (pRangeTileCounts)
|
||||
rangeTileCount = pRangeTileCounts[rangeIdx];
|
||||
}
|
||||
|
||||
if (!(rangeFlag & D3D11_TILE_RANGE_SKIP)) {
|
||||
if (regionCoord.Subresource >= pageTable->getSubresourceCount())
|
||||
return E_INVALIDARG;
|
||||
|
||||
if (regionSize.bUseBox && regionSize.NumTiles !=
|
||||
regionSize.Width * regionSize.Height * regionSize.Depth)
|
||||
return E_INVALIDARG;
|
||||
|
||||
VkOffset3D regionOffset = {
|
||||
int32_t(regionCoord.X),
|
||||
int32_t(regionCoord.Y),
|
||||
int32_t(regionCoord.Z) };
|
||||
|
||||
VkExtent3D regionExtent = {
|
||||
uint32_t(regionSize.Width),
|
||||
uint32_t(regionSize.Height),
|
||||
uint32_t(regionSize.Depth) };
|
||||
|
||||
uint32_t resourceTile = pageTable->computePageIndex(regionCoord.Subresource,
|
||||
regionOffset, regionExtent, !regionSize.bUseBox, regionTile);
|
||||
|
||||
// Fill in bind info for the current tile
|
||||
DxvkSparseBind bind = { };
|
||||
bind.dstPage = resourceTile;
|
||||
|
||||
if (rangeFlag & D3D11_TILE_RANGE_NULL) {
|
||||
bind.mode = DxvkSparseBindMode::Null;
|
||||
} else if (pTilePool) {
|
||||
bind.mode = DxvkSparseBindMode::Bind;
|
||||
bind.srcPage = rangeFlag & D3D11_TILE_RANGE_REUSE_SINGLE_TILE
|
||||
? rangeTileOffset
|
||||
: rangeTileOffset + rangeTile;
|
||||
} else {
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
|
||||
// Add bind info to the bind list, overriding
|
||||
// any existing bind for the same resource page
|
||||
if (resourceTile < pageTable->getPageCount()) {
|
||||
if (bindIndices[resourceTile] < bindInfo.binds.size())
|
||||
bindInfo.binds[bindIndices[resourceTile]] = bind;
|
||||
else
|
||||
bindInfo.binds.push_back(bind);
|
||||
}
|
||||
}
|
||||
|
||||
if (++regionTile == regionSize.NumTiles) {
|
||||
regionTile = 0;
|
||||
regionIdx += 1;
|
||||
}
|
||||
|
||||
if (++rangeTile == rangeTileCount) {
|
||||
rangeTile = 0;
|
||||
rangeIdx += 1;
|
||||
}
|
||||
}
|
||||
|
||||
// Translate flags. The backend benefits from NO_OVERWRITE since
|
||||
// otherwise we have to serialize execution of the current command
|
||||
// buffer, the sparse binding operation, and subsequent commands.
|
||||
// With NO_OVERWRITE, we can execute it more or less asynchronously.
|
||||
DxvkSparseBindFlags flags = (Flags & D3D11_TILE_MAPPING_NO_OVERWRITE)
|
||||
? DxvkSparseBindFlags(DxvkSparseBindFlag::SkipSynchronization)
|
||||
: DxvkSparseBindFlags();
|
||||
|
||||
EmitCs([
|
||||
cBindInfo = std::move(bindInfo),
|
||||
cFlags = flags
|
||||
] (DxvkContext* ctx) {
|
||||
ctx->updatePageTable(cBindInfo, cFlags);
|
||||
});
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::UpdateTiles(
|
||||
ID3D11Resource* pDestTiledResource,
|
||||
const D3D11_TILED_RESOURCE_COORDINATE* pDestTileRegionStartCoordinate,
|
||||
const D3D11_TILE_REGION_SIZE* pDestTileRegionSize,
|
||||
const void* pSourceTileData,
|
||||
UINT Flags) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
if (!pDestTiledResource || !pSourceTileData)
|
||||
return;
|
||||
|
||||
// Allocate staging memory and copy source data into it, at a
|
||||
// 64k page granularity. It is not clear whether this behaviour
|
||||
// is correct in case we're writing to incmplete pages.
|
||||
VkDeviceSize bufferSize = pDestTileRegionSize->NumTiles * SparseMemoryPageSize;
|
||||
|
||||
DxvkBufferSlice slice = AllocStagingBuffer(bufferSize);
|
||||
std::memcpy(slice.mapPtr(0), pSourceTileData, bufferSize);
|
||||
|
||||
// Fix up flags. The runtime probably validates this in some
|
||||
// way but our internal function relies on correct flags anyway.
|
||||
Flags &= D3D11_TILE_MAPPING_NO_OVERWRITE;
|
||||
Flags |= D3D11_TILE_COPY_LINEAR_BUFFER_TO_SWIZZLED_TILED_RESOURCE;
|
||||
|
||||
CopyTiledResourceData(pDestTiledResource,
|
||||
pDestTileRegionStartCoordinate,
|
||||
pDestTileRegionSize, slice, Flags);
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
BOOL STDMETHODCALLTYPE D3D11CommonContext<ContextType>::IsAnnotationEnabled() {
|
||||
return m_annotation.GetStatus();
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::SetMarkerInt(
|
||||
LPCWSTR pLabel,
|
||||
INT Data) {
|
||||
// Not implemented in the backend, ignore
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::BeginEventInt(
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::BeginEventInt(
|
||||
LPCWSTR pLabel,
|
||||
INT Data) {
|
||||
// Not implemented in the backend, ignore
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::EndEvent() {
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::EndEvent() {
|
||||
// Not implemented in the backend, ignore
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::GetHardwareProtectionState(
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::GetHardwareProtectionState(
|
||||
BOOL* pHwProtectionEnable) {
|
||||
static bool s_errorShown = false;
|
||||
|
||||
if (!std::exchange(s_errorShown, true))
|
||||
Logger::err("D3D11DeviceContext::GetHardwareProtectionState: Not implemented");
|
||||
|
||||
|
||||
if (pHwProtectionEnable)
|
||||
*pHwProtectionEnable = FALSE;
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::SetHardwareProtectionState(
|
||||
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::SetHardwareProtectionState(
|
||||
BOOL HwProtectionEnable) {
|
||||
static bool s_errorShown = false;
|
||||
|
||||
@ -2863,22 +3036,23 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContext::TransitionSurfaceLayout(
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11CommonContext<ContextType>::TransitionSurfaceLayout(
|
||||
IDXGIVkInteropSurface* pSurface,
|
||||
const VkImageSubresourceRange* pSubresources,
|
||||
VkImageLayout OldLayout,
|
||||
VkImageLayout NewLayout) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
|
||||
// Get the underlying D3D11 resource
|
||||
Com<ID3D11Resource> resource;
|
||||
|
||||
|
||||
pSurface->QueryInterface(__uuidof(ID3D11Resource),
|
||||
reinterpret_cast<void**>(&resource));
|
||||
|
||||
|
||||
// Get the texture from that resource
|
||||
D3D11CommonTexture* texture = GetCommonTexture(resource.ptr());
|
||||
|
||||
|
||||
EmitCs([
|
||||
cImage = texture->GetImage(),
|
||||
cSubresources = *pSubresources,
|
||||
@ -2890,9 +3064,46 @@ namespace dxvk {
|
||||
cOldLayout, cNewLayout);
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::ApplyInputLayout() {
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
DxvkCsChunkRef D3D11CommonContext<ContextType>::AllocCsChunk() {
|
||||
return m_parent->AllocCsChunk(m_csFlags);
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
DxvkDataSlice D3D11CommonContext<ContextType>::AllocUpdateBufferSlice(size_t Size) {
|
||||
constexpr size_t UpdateBufferSize = 1 * 1024 * 1024;
|
||||
|
||||
if (Size >= UpdateBufferSize) {
|
||||
Rc<DxvkDataBuffer> buffer = new DxvkDataBuffer(Size);
|
||||
return buffer->alloc(Size);
|
||||
} else {
|
||||
if (m_updateBuffer == nullptr)
|
||||
m_updateBuffer = new DxvkDataBuffer(UpdateBufferSize);
|
||||
|
||||
DxvkDataSlice slice = m_updateBuffer->alloc(Size);
|
||||
|
||||
if (slice.ptr() == nullptr) {
|
||||
m_updateBuffer = new DxvkDataBuffer(UpdateBufferSize);
|
||||
slice = m_updateBuffer->alloc(Size);
|
||||
}
|
||||
|
||||
return slice;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
DxvkBufferSlice D3D11CommonContext<ContextType>::AllocStagingBuffer(
|
||||
VkDeviceSize Size) {
|
||||
return m_staging.alloc(256, Size);
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::ApplyInputLayout() {
|
||||
auto inputLayout = m_state.ia.inputLayout.prvRef();
|
||||
|
||||
if (likely(inputLayout != nullptr)) {
|
||||
@ -2907,9 +3118,10 @@ namespace dxvk {
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::ApplyPrimitiveTopology() {
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::ApplyPrimitiveTopology() {
|
||||
D3D11_PRIMITIVE_TOPOLOGY topology = m_state.ia.primitiveTopology;
|
||||
DxvkInputAssemblyState iaState = { };
|
||||
|
||||
@ -2940,9 +3152,10 @@ namespace dxvk {
|
||||
ctx->setInputAssemblyState(iaState);
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::ApplyBlendState() {
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::ApplyBlendState() {
|
||||
if (m_state.om.cbState != nullptr) {
|
||||
EmitCs([
|
||||
cBlendState = m_state.om.cbState,
|
||||
@ -2967,9 +3180,10 @@ namespace dxvk {
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::ApplyBlendFactor() {
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::ApplyBlendFactor() {
|
||||
EmitCs([
|
||||
cBlendConstants = DxvkBlendConstants {
|
||||
m_state.om.blendFactor[0], m_state.om.blendFactor[1],
|
||||
@ -2978,9 +3192,10 @@ namespace dxvk {
|
||||
ctx->setBlendConstants(cBlendConstants);
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::ApplyDepthStencilState() {
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::ApplyDepthStencilState() {
|
||||
if (m_state.om.dsState != nullptr) {
|
||||
EmitCs([
|
||||
cDepthStencilState = m_state.om.dsState
|
||||
@ -2998,7 +3213,8 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::ApplyStencilRef() {
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::ApplyStencilRef() {
|
||||
EmitCs([
|
||||
cStencilRef = m_state.om.stencilRef
|
||||
] (DxvkContext* ctx) {
|
||||
@ -3007,7 +3223,8 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::ApplyRasterizerState() {
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::ApplyRasterizerState() {
|
||||
if (m_state.rs.state != nullptr) {
|
||||
EmitCs([
|
||||
cRasterizerState = m_state.rs.state
|
||||
@ -3023,9 +3240,32 @@ namespace dxvk {
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::ApplyViewportState() {
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::ApplyRasterizerSampleCount() {
|
||||
DxbcPushConstants pc;
|
||||
pc.rasterizerSampleCount = m_state.om.sampleCount;
|
||||
|
||||
if (unlikely(!m_state.om.sampleCount)) {
|
||||
pc.rasterizerSampleCount = m_state.rs.state
|
||||
? m_state.rs.state->Desc()->ForcedSampleCount
|
||||
: 0;
|
||||
|
||||
if (!pc.rasterizerSampleCount)
|
||||
pc.rasterizerSampleCount = 1;
|
||||
}
|
||||
|
||||
EmitCs([
|
||||
cPushConstants = pc
|
||||
] (DxvkContext* ctx) {
|
||||
ctx->pushConstants(0, sizeof(cPushConstants), &cPushConstants);
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::ApplyViewportState() {
|
||||
std::array<VkViewport, D3D11_VIEWPORT_AND_SCISSORRECT_OBJECT_COUNT_PER_PIPELINE> viewports;
|
||||
std::array<VkRect2D, D3D11_VIEWPORT_AND_SCISSORRECT_OBJECT_COUNT_PER_PIPELINE> scissors;
|
||||
|
||||
@ -3044,25 +3284,25 @@ namespace dxvk {
|
||||
// corner so we can get away with flipping the viewport.
|
||||
for (uint32_t i = 0; i < m_state.rs.numViewports; i++) {
|
||||
const D3D11_VIEWPORT& vp = m_state.rs.viewports[i];
|
||||
|
||||
|
||||
viewports[i] = VkViewport {
|
||||
vp.TopLeftX, vp.Height + vp.TopLeftY,
|
||||
vp.Width, -vp.Height,
|
||||
vp.MinDepth, vp.MaxDepth,
|
||||
};
|
||||
}
|
||||
|
||||
|
||||
// Scissor rectangles. Vulkan does not provide an easy way
|
||||
// to disable the scissor test, so we'll have to set scissor
|
||||
// rects that are at least as large as the framebuffer.
|
||||
bool enableScissorTest = false;
|
||||
|
||||
|
||||
if (m_state.rs.state != nullptr) {
|
||||
D3D11_RASTERIZER_DESC rsDesc;
|
||||
m_state.rs.state->GetDesc(&rsDesc);
|
||||
enableScissorTest = rsDesc.ScissorEnable;
|
||||
}
|
||||
|
||||
|
||||
for (uint32_t i = 0; i < m_state.rs.numViewports; i++) {
|
||||
if (!enableScissorTest) {
|
||||
scissors[i] = VkRect2D {
|
||||
@ -3076,23 +3316,23 @@ namespace dxvk {
|
||||
VkExtent2D { 0, 0 } };
|
||||
} else {
|
||||
D3D11_RECT sr = m_state.rs.scissors[i];
|
||||
|
||||
|
||||
VkOffset2D srPosA;
|
||||
srPosA.x = std::max<int32_t>(0, sr.left);
|
||||
srPosA.y = std::max<int32_t>(0, sr.top);
|
||||
|
||||
|
||||
VkOffset2D srPosB;
|
||||
srPosB.x = std::max<int32_t>(srPosA.x, sr.right);
|
||||
srPosB.y = std::max<int32_t>(srPosA.y, sr.bottom);
|
||||
|
||||
|
||||
VkExtent2D srSize;
|
||||
srSize.width = uint32_t(srPosB.x - srPosA.x);
|
||||
srSize.height = uint32_t(srPosB.y - srPosA.y);
|
||||
|
||||
|
||||
scissors[i] = VkRect2D { srPosA, srSize };
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
if (likely(viewportCount == 1)) {
|
||||
EmitCs([
|
||||
cViewport = viewports[0],
|
||||
@ -3116,84 +3356,136 @@ namespace dxvk {
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void D3D11DeviceContext::BindShader(
|
||||
void D3D11CommonContext<ContextType>::BindShader(
|
||||
const D3D11CommonShader* pShaderModule) {
|
||||
// Bind the shader and the ICB at once
|
||||
EmitCs([
|
||||
cSlice = pShaderModule != nullptr
|
||||
&& pShaderModule->GetIcb() != nullptr
|
||||
? DxvkBufferSlice(pShaderModule->GetIcb())
|
||||
: DxvkBufferSlice(),
|
||||
cShader = pShaderModule != nullptr
|
||||
? pShaderModule->GetShader()
|
||||
: nullptr
|
||||
] (DxvkContext* ctx) {
|
||||
VkShaderStageFlagBits stage = GetShaderStage(ShaderStage);
|
||||
if (pShaderModule) {
|
||||
auto buffer = pShaderModule->GetIcb();
|
||||
auto shader = pShaderModule->GetShader();
|
||||
|
||||
uint32_t slotId = computeConstantBufferBinding(ShaderStage,
|
||||
D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT);
|
||||
if (unlikely(shader->needsLibraryCompile()))
|
||||
m_device->requestCompileShader(shader);
|
||||
|
||||
ctx->bindShader (stage, cShader);
|
||||
ctx->bindResourceBuffer(slotId, cSlice);
|
||||
});
|
||||
EmitCs([
|
||||
cBuffer = std::move(buffer),
|
||||
cShader = std::move(shader)
|
||||
] (DxvkContext* ctx) mutable {
|
||||
constexpr VkShaderStageFlagBits stage = GetShaderStage(ShaderStage);
|
||||
|
||||
uint32_t slotId = computeConstantBufferBinding(ShaderStage,
|
||||
D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT);
|
||||
|
||||
ctx->bindShader<stage>(
|
||||
Forwarder::move(cShader));
|
||||
ctx->bindUniformBuffer(stage, slotId,
|
||||
Forwarder::move(cBuffer));
|
||||
});
|
||||
} else {
|
||||
EmitCs([] (DxvkContext* ctx) {
|
||||
constexpr VkShaderStageFlagBits stage = GetShaderStage(ShaderStage);
|
||||
|
||||
uint32_t slotId = computeConstantBufferBinding(ShaderStage,
|
||||
D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT);
|
||||
|
||||
ctx->bindShader<stage>(nullptr);
|
||||
ctx->bindUniformBuffer(stage, slotId, DxvkBufferSlice());
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::BindFramebuffer() {
|
||||
static VkDepthBiasRepresentationEXT FormatToDepthBiasRepresentation(DXGI_FORMAT format) {
|
||||
switch (format) {
|
||||
default:
|
||||
case DXGI_FORMAT_D32_FLOAT_S8X24_UINT:
|
||||
case DXGI_FORMAT_D32_FLOAT:
|
||||
return VK_DEPTH_BIAS_REPRESENTATION_LEAST_REPRESENTABLE_VALUE_FORMAT_EXT;
|
||||
|
||||
case DXGI_FORMAT_D24_UNORM_S8_UINT:
|
||||
case DXGI_FORMAT_D16_UNORM:
|
||||
return VK_DEPTH_BIAS_REPRESENTATION_LEAST_REPRESENTABLE_VALUE_FORCE_UNORM_EXT;
|
||||
}
|
||||
}
|
||||
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::BindFramebuffer() {
|
||||
DxvkDepthBiasRepresentation depthBiasRepresentation =
|
||||
{ VK_DEPTH_BIAS_REPRESENTATION_LEAST_REPRESENTABLE_VALUE_FORMAT_EXT,
|
||||
m_device->features().extDepthBiasControl.depthBiasExact };
|
||||
DxvkRenderTargets attachments;
|
||||
|
||||
uint32_t sampleCount = 0;
|
||||
|
||||
// D3D11 doesn't have the concept of a framebuffer object,
|
||||
// so we'll just create a new one every time the render
|
||||
// target bindings are updated. Set up the attachments.
|
||||
for (UINT i = 0; i < m_state.om.renderTargetViews.size(); i++) {
|
||||
if (m_state.om.renderTargetViews[i] != nullptr) {
|
||||
for (UINT i = 0; i < m_state.om.rtvs.size(); i++) {
|
||||
if (m_state.om.rtvs[i] != nullptr) {
|
||||
attachments.color[i] = {
|
||||
m_state.om.renderTargetViews[i]->GetImageView(),
|
||||
m_state.om.renderTargetViews[i]->GetRenderLayout() };
|
||||
m_state.om.rtvs[i]->GetImageView(),
|
||||
m_state.om.rtvs[i]->GetRenderLayout() };
|
||||
sampleCount = m_state.om.rtvs[i]->GetSampleCount();
|
||||
}
|
||||
}
|
||||
|
||||
if (m_state.om.depthStencilView != nullptr) {
|
||||
|
||||
if (m_state.om.dsv != nullptr) {
|
||||
attachments.depth = {
|
||||
m_state.om.depthStencilView->GetImageView(),
|
||||
m_state.om.depthStencilView->GetRenderLayout() };
|
||||
m_state.om.dsv->GetImageView(),
|
||||
m_state.om.dsv->GetRenderLayout() };
|
||||
sampleCount = m_state.om.dsv->GetSampleCount();
|
||||
|
||||
if (m_device->features().extDepthBiasControl.leastRepresentableValueForceUnormRepresentation)
|
||||
depthBiasRepresentation.depthBiasRepresentation = FormatToDepthBiasRepresentation(m_state.om.dsv->GetViewFormat());
|
||||
}
|
||||
|
||||
|
||||
// Create and bind the framebuffer object to the context
|
||||
EmitCs([
|
||||
cAttachments = std::move(attachments)
|
||||
] (DxvkContext* ctx) {
|
||||
ctx->bindRenderTargets(cAttachments);
|
||||
cAttachments = std::move(attachments),
|
||||
cRepresentation = depthBiasRepresentation
|
||||
] (DxvkContext* ctx) mutable {
|
||||
ctx->setDepthBiasRepresentation(cRepresentation);
|
||||
ctx->bindRenderTargets(Forwarder::move(cAttachments), 0u);
|
||||
});
|
||||
|
||||
// If necessary, update push constant for the sample count
|
||||
if (m_state.om.sampleCount != sampleCount) {
|
||||
m_state.om.sampleCount = sampleCount;
|
||||
ApplyRasterizerSampleCount();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::BindDrawBuffers(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::BindDrawBuffers(
|
||||
D3D11Buffer* pBufferForArgs,
|
||||
D3D11Buffer* pBufferForCount) {
|
||||
EmitCs([
|
||||
cArgBuffer = pBufferForArgs ? pBufferForArgs->GetBufferSlice() : DxvkBufferSlice(),
|
||||
cCntBuffer = pBufferForCount ? pBufferForCount->GetBufferSlice() : DxvkBufferSlice()
|
||||
] (DxvkContext* ctx) {
|
||||
ctx->bindDrawBuffers(cArgBuffer, cCntBuffer);
|
||||
] (DxvkContext* ctx) mutable {
|
||||
ctx->bindDrawBuffers(
|
||||
Forwarder::move(cArgBuffer),
|
||||
Forwarder::move(cCntBuffer));
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::BindVertexBuffer(
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::BindVertexBuffer(
|
||||
UINT Slot,
|
||||
D3D11Buffer* pBuffer,
|
||||
UINT Offset,
|
||||
UINT Stride) {
|
||||
if (likely(pBuffer != nullptr)) {
|
||||
if (pBuffer) {
|
||||
EmitCs([
|
||||
cSlotId = Slot,
|
||||
cBufferSlice = pBuffer->GetBufferSlice(Offset),
|
||||
cStride = Stride
|
||||
] (DxvkContext* ctx) {
|
||||
ctx->bindVertexBuffer(cSlotId, cBufferSlice, cStride);
|
||||
] (DxvkContext* ctx) mutable {
|
||||
ctx->bindVertexBuffer(cSlotId,
|
||||
Forwarder::move(cBufferSlice),
|
||||
cStride);
|
||||
});
|
||||
} else {
|
||||
EmitCs([
|
||||
@ -3205,121 +3497,316 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::BindIndexBuffer(
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::BindVertexBufferRange(
|
||||
UINT Slot,
|
||||
D3D11Buffer* pBuffer,
|
||||
UINT Offset,
|
||||
UINT Stride) {
|
||||
if (pBuffer) {
|
||||
VkDeviceSize offset = Offset;
|
||||
VkDeviceSize length = pBuffer->GetRemainingSize(Offset);
|
||||
|
||||
EmitCs([
|
||||
cSlotId = Slot,
|
||||
cBufferOffset = offset,
|
||||
cBufferLength = length,
|
||||
cStride = Stride
|
||||
] (DxvkContext* ctx) mutable {
|
||||
ctx->bindVertexBufferRange(cSlotId,
|
||||
cBufferOffset, cBufferLength, cStride);
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::BindIndexBuffer(
|
||||
D3D11Buffer* pBuffer,
|
||||
UINT Offset,
|
||||
DXGI_FORMAT Format) {
|
||||
VkIndexType indexType = Format == DXGI_FORMAT_R16_UINT
|
||||
? VK_INDEX_TYPE_UINT16
|
||||
: VK_INDEX_TYPE_UINT32;
|
||||
|
||||
EmitCs([
|
||||
cBufferSlice = pBuffer != nullptr ? pBuffer->GetBufferSlice(Offset) : DxvkBufferSlice(),
|
||||
cIndexType = indexType
|
||||
] (DxvkContext* ctx) {
|
||||
ctx->bindIndexBuffer(cBufferSlice, cIndexType);
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::BindXfbBuffer(
|
||||
if (pBuffer) {
|
||||
EmitCs([
|
||||
cBufferSlice = pBuffer->GetBufferSlice(Offset),
|
||||
cIndexType = indexType
|
||||
] (DxvkContext* ctx) mutable {
|
||||
ctx->bindIndexBuffer(
|
||||
Forwarder::move(cBufferSlice),
|
||||
cIndexType);
|
||||
});
|
||||
} else {
|
||||
EmitCs([
|
||||
cIndexType = indexType
|
||||
] (DxvkContext* ctx) {
|
||||
ctx->bindIndexBuffer(DxvkBufferSlice(), cIndexType);
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::BindIndexBufferRange(
|
||||
D3D11Buffer* pBuffer,
|
||||
UINT Offset,
|
||||
DXGI_FORMAT Format) {
|
||||
if (pBuffer) {
|
||||
VkIndexType indexType = Format == DXGI_FORMAT_R16_UINT
|
||||
? VK_INDEX_TYPE_UINT16
|
||||
: VK_INDEX_TYPE_UINT32;
|
||||
|
||||
VkDeviceSize offset = Offset;
|
||||
VkDeviceSize length = pBuffer->GetRemainingSize(Offset);
|
||||
|
||||
EmitCs([
|
||||
cBufferOffset = offset,
|
||||
cBufferLength = length,
|
||||
cIndexType = indexType
|
||||
] (DxvkContext* ctx) mutable {
|
||||
ctx->bindIndexBufferRange(
|
||||
cBufferOffset, cBufferLength,
|
||||
cIndexType);
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::BindXfbBuffer(
|
||||
UINT Slot,
|
||||
D3D11Buffer* pBuffer,
|
||||
UINT Offset) {
|
||||
DxvkBufferSlice bufferSlice;
|
||||
DxvkBufferSlice counterSlice;
|
||||
|
||||
if (pBuffer != nullptr) {
|
||||
bufferSlice = pBuffer->GetBufferSlice();
|
||||
counterSlice = pBuffer->GetSOCounter();
|
||||
if (pBuffer) {
|
||||
EmitCs([
|
||||
cSlotId = Slot,
|
||||
cOffset = Offset,
|
||||
cBufferSlice = pBuffer->GetBufferSlice(),
|
||||
cCounterSlice = pBuffer->GetSOCounter()
|
||||
] (DxvkContext* ctx) mutable {
|
||||
if (cCounterSlice.defined() && cOffset != ~0u) {
|
||||
ctx->updateBuffer(
|
||||
cCounterSlice.buffer(),
|
||||
cCounterSlice.offset(),
|
||||
sizeof(cOffset),
|
||||
&cOffset);
|
||||
}
|
||||
|
||||
ctx->bindXfbBuffer(cSlotId,
|
||||
Forwarder::move(cBufferSlice),
|
||||
Forwarder::move(cCounterSlice));
|
||||
});
|
||||
} else {
|
||||
EmitCs([
|
||||
cSlotId = Slot
|
||||
] (DxvkContext* ctx) {
|
||||
ctx->bindXfbBuffer(cSlotId,
|
||||
DxvkBufferSlice(),
|
||||
DxvkBufferSlice());
|
||||
});
|
||||
}
|
||||
|
||||
EmitCs([
|
||||
cSlotId = Slot,
|
||||
cOffset = Offset,
|
||||
cBufferSlice = bufferSlice,
|
||||
cCounterSlice = counterSlice
|
||||
] (DxvkContext* ctx) {
|
||||
if (cCounterSlice.defined() && cOffset != ~0u) {
|
||||
ctx->updateBuffer(
|
||||
cCounterSlice.buffer(),
|
||||
cCounterSlice.offset(),
|
||||
sizeof(cOffset),
|
||||
&cOffset);
|
||||
}
|
||||
|
||||
ctx->bindXfbBuffer(cSlotId, cBufferSlice, cCounterSlice);
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::BindConstantBuffer(
|
||||
template<typename ContextType>
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void D3D11CommonContext<ContextType>::BindConstantBuffer(
|
||||
UINT Slot,
|
||||
D3D11Buffer* pBuffer,
|
||||
UINT Offset,
|
||||
UINT Length) {
|
||||
EmitCs([
|
||||
cSlotId = Slot,
|
||||
cBufferSlice = Length ? pBuffer->GetBufferSlice(16 * Offset, 16 * Length) : DxvkBufferSlice()
|
||||
] (DxvkContext* ctx) {
|
||||
ctx->bindResourceBuffer(cSlotId, cBufferSlice);
|
||||
});
|
||||
if (pBuffer) {
|
||||
EmitCs([
|
||||
cSlotId = Slot,
|
||||
cBufferSlice = pBuffer->GetBufferSlice(16 * Offset, 16 * Length)
|
||||
] (DxvkContext* ctx) mutable {
|
||||
VkShaderStageFlagBits stage = GetShaderStage(ShaderStage);
|
||||
ctx->bindUniformBuffer(stage, cSlotId,
|
||||
Forwarder::move(cBufferSlice));
|
||||
});
|
||||
} else {
|
||||
EmitCs([
|
||||
cSlotId = Slot
|
||||
] (DxvkContext* ctx) {
|
||||
VkShaderStageFlagBits stage = GetShaderStage(ShaderStage);
|
||||
ctx->bindUniformBuffer(stage, cSlotId, DxvkBufferSlice());
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::BindSampler(
|
||||
template<typename ContextType>
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void D3D11CommonContext<ContextType>::BindConstantBufferRange(
|
||||
UINT Slot,
|
||||
UINT Offset,
|
||||
UINT Length) {
|
||||
EmitCs([
|
||||
cSlotId = Slot,
|
||||
cOffset = 16 * Offset,
|
||||
cLength = 16 * Length
|
||||
] (DxvkContext* ctx) {
|
||||
VkShaderStageFlagBits stage = GetShaderStage(ShaderStage);
|
||||
ctx->bindUniformBufferRange(stage, cSlotId, cOffset, cLength);
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void D3D11CommonContext<ContextType>::BindSampler(
|
||||
UINT Slot,
|
||||
D3D11SamplerState* pSampler) {
|
||||
EmitCs([
|
||||
cSlotId = Slot,
|
||||
cSampler = pSampler != nullptr ? pSampler->GetDXVKSampler() : nullptr
|
||||
] (DxvkContext* ctx) {
|
||||
ctx->bindResourceSampler(cSlotId, cSampler);
|
||||
});
|
||||
if (pSampler) {
|
||||
EmitCs([
|
||||
cSlotId = Slot,
|
||||
cSampler = pSampler->GetDXVKSampler()
|
||||
] (DxvkContext* ctx) mutable {
|
||||
VkShaderStageFlagBits stage = GetShaderStage(ShaderStage);
|
||||
ctx->bindResourceSampler(stage, cSlotId,
|
||||
Forwarder::move(cSampler));
|
||||
});
|
||||
} else {
|
||||
EmitCs([
|
||||
cSlotId = Slot
|
||||
] (DxvkContext* ctx) {
|
||||
VkShaderStageFlagBits stage = GetShaderStage(ShaderStage);
|
||||
ctx->bindResourceSampler(stage, cSlotId, nullptr);
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::BindShaderResource(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void D3D11CommonContext<ContextType>::BindShaderResource(
|
||||
UINT Slot,
|
||||
D3D11ShaderResourceView* pResource) {
|
||||
EmitCs([
|
||||
cSlotId = Slot,
|
||||
cImageView = pResource != nullptr ? pResource->GetImageView() : nullptr,
|
||||
cBufferView = pResource != nullptr ? pResource->GetBufferView() : nullptr
|
||||
] (DxvkContext* ctx) {
|
||||
ctx->bindResourceView(cSlotId, cImageView, cBufferView);
|
||||
});
|
||||
if (pResource) {
|
||||
if (pResource->GetViewInfo().Dimension != D3D11_RESOURCE_DIMENSION_BUFFER) {
|
||||
EmitCs([
|
||||
cSlotId = Slot,
|
||||
cView = pResource->GetImageView()
|
||||
] (DxvkContext* ctx) mutable {
|
||||
VkShaderStageFlagBits stage = GetShaderStage(ShaderStage);
|
||||
ctx->bindResourceImageView(stage, cSlotId,
|
||||
Forwarder::move(cView));
|
||||
});
|
||||
} else {
|
||||
EmitCs([
|
||||
cSlotId = Slot,
|
||||
cView = pResource->GetBufferView()
|
||||
] (DxvkContext* ctx) mutable {
|
||||
VkShaderStageFlagBits stage = GetShaderStage(ShaderStage);
|
||||
ctx->bindResourceBufferView(stage, cSlotId,
|
||||
Forwarder::move(cView));
|
||||
});
|
||||
}
|
||||
} else {
|
||||
EmitCs([
|
||||
cSlotId = Slot
|
||||
] (DxvkContext* ctx) {
|
||||
VkShaderStageFlagBits stage = GetShaderStage(ShaderStage);
|
||||
ctx->bindResourceImageView(stage, cSlotId, nullptr);
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::BindUnorderedAccessView(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void D3D11CommonContext<ContextType>::BindUnorderedAccessView(
|
||||
UINT UavSlot,
|
||||
D3D11UnorderedAccessView* pUav,
|
||||
UINT CtrSlot,
|
||||
UINT Counter) {
|
||||
EmitCs([
|
||||
cUavSlotId = UavSlot,
|
||||
cCtrSlotId = CtrSlot,
|
||||
cImageView = pUav != nullptr ? pUav->GetImageView() : nullptr,
|
||||
cBufferView = pUav != nullptr ? pUav->GetBufferView() : nullptr,
|
||||
cCounterSlice = pUav != nullptr ? pUav->GetCounterSlice() : DxvkBufferSlice(),
|
||||
cCounterValue = Counter
|
||||
] (DxvkContext* ctx) {
|
||||
if (cCounterSlice.defined() && cCounterValue != ~0u) {
|
||||
ctx->updateBuffer(
|
||||
cCounterSlice.buffer(),
|
||||
cCounterSlice.offset(),
|
||||
sizeof(uint32_t),
|
||||
&cCounterValue);
|
||||
}
|
||||
if (pUav) {
|
||||
if (pUav->GetViewInfo().Dimension == D3D11_RESOURCE_DIMENSION_BUFFER) {
|
||||
EmitCs([
|
||||
cUavSlotId = UavSlot,
|
||||
cCtrSlotId = CtrSlot,
|
||||
cBufferView = pUav->GetBufferView(),
|
||||
cCounterView = pUav->GetCounterView(),
|
||||
cCounterValue = Counter
|
||||
] (DxvkContext* ctx) mutable {
|
||||
VkShaderStageFlags stages = ShaderStage == DxbcProgramType::ComputeShader
|
||||
? VK_SHADER_STAGE_COMPUTE_BIT
|
||||
: VK_SHADER_STAGE_ALL_GRAPHICS;
|
||||
|
||||
ctx->bindResourceView (cUavSlotId, cImageView, cBufferView);
|
||||
ctx->bindResourceBuffer (cCtrSlotId, cCounterSlice);
|
||||
});
|
||||
if (cCounterView != nullptr && cCounterValue != ~0u) {
|
||||
auto counterSlice = cCounterView->slice();
|
||||
|
||||
ctx->updateBuffer(
|
||||
counterSlice.buffer(),
|
||||
counterSlice.offset(),
|
||||
sizeof(uint32_t),
|
||||
&cCounterValue);
|
||||
}
|
||||
|
||||
ctx->bindResourceBufferView(stages, cUavSlotId,
|
||||
Forwarder::move(cBufferView));
|
||||
ctx->bindResourceBufferView(stages, cCtrSlotId,
|
||||
Forwarder::move(cCounterView));
|
||||
});
|
||||
} else {
|
||||
EmitCs([
|
||||
cUavSlotId = UavSlot,
|
||||
cCtrSlotId = CtrSlot,
|
||||
cImageView = pUav->GetImageView()
|
||||
] (DxvkContext* ctx) mutable {
|
||||
VkShaderStageFlags stages = ShaderStage == DxbcProgramType::ComputeShader
|
||||
? VK_SHADER_STAGE_COMPUTE_BIT
|
||||
: VK_SHADER_STAGE_ALL_GRAPHICS;
|
||||
|
||||
ctx->bindResourceImageView(stages, cUavSlotId,
|
||||
Forwarder::move(cImageView));
|
||||
ctx->bindResourceBufferView(stages, cCtrSlotId, nullptr);
|
||||
});
|
||||
}
|
||||
} else {
|
||||
EmitCs([
|
||||
cUavSlotId = UavSlot,
|
||||
cCtrSlotId = CtrSlot
|
||||
] (DxvkContext* ctx) {
|
||||
VkShaderStageFlags stages = ShaderStage == DxbcProgramType::ComputeShader
|
||||
? VK_SHADER_STAGE_COMPUTE_BIT
|
||||
: VK_SHADER_STAGE_ALL_GRAPHICS;
|
||||
|
||||
ctx->bindResourceImageView(stages, cUavSlotId, nullptr);
|
||||
ctx->bindResourceBufferView(stages, cCtrSlotId, nullptr);
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::CopyBuffer(
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
VkClearValue D3D11CommonContext<ContextType>::ConvertColorValue(
|
||||
const FLOAT Color[4],
|
||||
const DxvkFormatInfo* pFormatInfo) {
|
||||
VkClearValue result;
|
||||
|
||||
if (pFormatInfo->aspectMask & VK_IMAGE_ASPECT_COLOR_BIT) {
|
||||
for (uint32_t i = 0; i < 4; i++) {
|
||||
if (pFormatInfo->flags.test(DxvkFormatFlag::SampledUInt))
|
||||
result.color.uint32[i] = uint32_t(std::max(0.0f, Color[i]));
|
||||
else if (pFormatInfo->flags.test(DxvkFormatFlag::SampledSInt))
|
||||
result.color.int32[i] = int32_t(Color[i]);
|
||||
else
|
||||
result.color.float32[i] = Color[i];
|
||||
}
|
||||
} else {
|
||||
result.depthStencil.depth = Color[0];
|
||||
result.depthStencil.stencil = 0;
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::CopyBuffer(
|
||||
D3D11Buffer* pDstBuffer,
|
||||
VkDeviceSize DstOffset,
|
||||
D3D11Buffer* pSrcBuffer,
|
||||
@ -3356,13 +3843,14 @@ namespace dxvk {
|
||||
});
|
||||
|
||||
if (pDstBuffer->HasSequenceNumber())
|
||||
TrackBufferSequenceNumber(pDstBuffer);
|
||||
GetTypedContext()->TrackBufferSequenceNumber(pDstBuffer);
|
||||
if (pSrcBuffer->HasSequenceNumber())
|
||||
TrackBufferSequenceNumber(pSrcBuffer);
|
||||
GetTypedContext()->TrackBufferSequenceNumber(pSrcBuffer);
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::CopyImage(
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::CopyImage(
|
||||
D3D11CommonTexture* pDstTexture,
|
||||
const VkImageSubresourceLayers* pDstLayers,
|
||||
VkOffset3D DstOffset,
|
||||
@ -3371,20 +3859,16 @@ namespace dxvk {
|
||||
VkOffset3D SrcOffset,
|
||||
VkExtent3D SrcExtent) {
|
||||
// Image formats must be size-compatible
|
||||
auto dstFormatInfo = imageFormatInfo(pDstTexture->GetPackedFormat());
|
||||
auto srcFormatInfo = imageFormatInfo(pSrcTexture->GetPackedFormat());
|
||||
auto dstFormatInfo = lookupFormatInfo(pDstTexture->GetPackedFormat());
|
||||
auto srcFormatInfo = lookupFormatInfo(pSrcTexture->GetPackedFormat());
|
||||
|
||||
if (dstFormatInfo->elementSize != srcFormatInfo->elementSize) {
|
||||
Logger::err("D3D11: CopyImage: Incompatible texel size");
|
||||
if (dstFormatInfo->elementSize != srcFormatInfo->elementSize)
|
||||
return;
|
||||
}
|
||||
|
||||
// Sample counts must match
|
||||
if (pDstTexture->Desc()->SampleDesc.Count != pSrcTexture->Desc()->SampleDesc.Count) {
|
||||
Logger::err("D3D11: CopyImage: Incompatible sample count");
|
||||
if (pDstTexture->Desc()->SampleDesc.Count != pSrcTexture->Desc()->SampleDesc.Count)
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
// Obviously, the copy region must not be empty
|
||||
VkExtent3D dstMipExtent = pDstTexture->MipLevelExtent(pDstLayers->mipLevel);
|
||||
VkExtent3D srcMipExtent = pSrcTexture->MipLevelExtent(pSrcLayers->mipLevel);
|
||||
@ -3401,19 +3885,17 @@ namespace dxvk {
|
||||
|
||||
// Don't perform the copy if the offsets aren't block-aligned
|
||||
if (!util::isBlockAligned(SrcOffset, srcFormatInfo->blockSize)
|
||||
|| !util::isBlockAligned(DstOffset, dstFormatInfo->blockSize)) {
|
||||
Logger::err(str::format("D3D11: CopyImage: Unaligned block offset"));
|
||||
|| !util::isBlockAligned(DstOffset, dstFormatInfo->blockSize))
|
||||
return;
|
||||
}
|
||||
|
||||
// Clamp the image region in order to avoid out-of-bounds access
|
||||
VkExtent3D blockCount = util::computeBlockCount(SrcExtent, srcFormatInfo->blockSize);
|
||||
VkExtent3D dstBlockCount = util::computeMaxBlockCount(DstOffset, dstMipExtent, dstFormatInfo->blockSize);
|
||||
VkExtent3D srcBlockCount = util::computeMaxBlockCount(SrcOffset, srcMipExtent, srcFormatInfo->blockSize);
|
||||
|
||||
|
||||
blockCount = util::minExtent3D(blockCount, dstBlockCount);
|
||||
blockCount = util::minExtent3D(blockCount, srcBlockCount);
|
||||
|
||||
|
||||
SrcExtent = util::computeBlockExtent(blockCount, srcFormatInfo->blockSize);
|
||||
SrcExtent = util::snapExtent3D(SrcOffset, SrcExtent, srcMipExtent);
|
||||
|
||||
@ -3596,21 +4078,110 @@ namespace dxvk {
|
||||
|
||||
if (pDstTexture->HasSequenceNumber()) {
|
||||
for (uint32_t i = 0; i < pDstLayers->layerCount; i++) {
|
||||
TrackTextureSequenceNumber(pDstTexture, D3D11CalcSubresource(
|
||||
GetTypedContext()->TrackTextureSequenceNumber(pDstTexture, D3D11CalcSubresource(
|
||||
pDstLayers->mipLevel, pDstLayers->baseArrayLayer + i, pDstTexture->Desc()->MipLevels));
|
||||
}
|
||||
}
|
||||
|
||||
if (pSrcTexture->HasSequenceNumber()) {
|
||||
for (uint32_t i = 0; i < pSrcLayers->layerCount; i++) {
|
||||
TrackTextureSequenceNumber(pSrcTexture, D3D11CalcSubresource(
|
||||
GetTypedContext()->TrackTextureSequenceNumber(pSrcTexture, D3D11CalcSubresource(
|
||||
pSrcLayers->mipLevel, pSrcLayers->baseArrayLayer + i, pSrcTexture->Desc()->MipLevels));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::DiscardBuffer(
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::CopyTiledResourceData(
|
||||
ID3D11Resource* pResource,
|
||||
const D3D11_TILED_RESOURCE_COORDINATE* pRegionCoordinate,
|
||||
const D3D11_TILE_REGION_SIZE* pRegionSize,
|
||||
DxvkBufferSlice BufferSlice,
|
||||
UINT Flags) {
|
||||
Rc<DxvkPagedResource> resource = GetPagedResource(pResource);
|
||||
|
||||
// Do some validation based on page table properties
|
||||
auto pageTable = resource->getSparsePageTable();
|
||||
|
||||
if (!pageTable)
|
||||
return;
|
||||
|
||||
if (pRegionSize->bUseBox && pRegionSize->NumTiles !=
|
||||
pRegionSize->Width * pRegionSize->Height * pRegionSize->Depth)
|
||||
return;
|
||||
|
||||
if (pRegionSize->NumTiles > pageTable->getPageCount())
|
||||
return;
|
||||
|
||||
// Ignore call if buffer access would be out of bounds
|
||||
VkDeviceSize bufferSize = pRegionSize->NumTiles * SparseMemoryPageSize;
|
||||
|
||||
if (BufferSlice.length() < bufferSize)
|
||||
return;
|
||||
|
||||
// Compute list of tile indices to copy
|
||||
std::vector<uint32_t> tiles(pRegionSize->NumTiles);
|
||||
|
||||
for (uint32_t i = 0; i < pRegionSize->NumTiles; i++) {
|
||||
VkOffset3D regionOffset = {
|
||||
int32_t(pRegionCoordinate->X),
|
||||
int32_t(pRegionCoordinate->Y),
|
||||
int32_t(pRegionCoordinate->Z) };
|
||||
|
||||
VkExtent3D regionExtent = {
|
||||
uint32_t(pRegionSize->Width),
|
||||
uint32_t(pRegionSize->Height),
|
||||
uint32_t(pRegionSize->Depth) };
|
||||
|
||||
uint32_t tile = pageTable->computePageIndex(
|
||||
pRegionCoordinate->Subresource, regionOffset,
|
||||
regionExtent, !pRegionSize->bUseBox, i);
|
||||
|
||||
// Check that the tile is valid and not part of the mip tail
|
||||
auto tileInfo = pageTable->getPageInfo(tile);
|
||||
|
||||
if (tileInfo.type != DxvkSparsePageType::Buffer
|
||||
&& tileInfo.type != DxvkSparsePageType::Image)
|
||||
return;
|
||||
|
||||
tiles[i] = tile;
|
||||
}
|
||||
|
||||
// If D3D12 is anything to go by, not passing this flag will trigger
|
||||
// the other code path, regardless of whether TO_LINEAR_BUFFER is set.
|
||||
if (Flags & D3D11_TILE_COPY_LINEAR_BUFFER_TO_SWIZZLED_TILED_RESOURCE) {
|
||||
EmitCs([
|
||||
cResource = std::move(resource),
|
||||
cTiles = std::move(tiles),
|
||||
cBuffer = std::move(BufferSlice)
|
||||
] (DxvkContext* ctx) {
|
||||
ctx->copySparsePagesFromBuffer(
|
||||
cResource,
|
||||
cTiles.size(),
|
||||
cTiles.data(),
|
||||
cBuffer.buffer(),
|
||||
cBuffer.offset());
|
||||
});
|
||||
} else {
|
||||
EmitCs([
|
||||
cResource = std::move(resource),
|
||||
cTiles = std::move(tiles),
|
||||
cBuffer = std::move(BufferSlice)
|
||||
] (DxvkContext* ctx) {
|
||||
ctx->copySparsePagesToBuffer(
|
||||
cBuffer.buffer(),
|
||||
cBuffer.offset(),
|
||||
cResource,
|
||||
cTiles.size(),
|
||||
cTiles.data());
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::DiscardBuffer(
|
||||
ID3D11Resource* pResource) {
|
||||
auto buffer = static_cast<D3D11Buffer*>(pResource);
|
||||
|
||||
@ -3623,7 +4194,8 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::DiscardTexture(
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::DiscardTexture(
|
||||
ID3D11Resource* pResource,
|
||||
UINT Subresource) {
|
||||
auto texture = GetCommonTexture(pResource);
|
||||
@ -3637,7 +4209,866 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::UpdateBuffer(
|
||||
template<typename ContextType>
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void D3D11CommonContext<ContextType>::GetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppConstantBuffers,
|
||||
UINT* pFirstConstant,
|
||||
UINT* pNumConstants) {
|
||||
const auto& bindings = m_state.cbv[ShaderStage];
|
||||
|
||||
for (uint32_t i = 0; i < NumBuffers; i++) {
|
||||
const bool inRange = StartSlot + i < bindings.buffers.size();
|
||||
|
||||
if (ppConstantBuffers) {
|
||||
ppConstantBuffers[i] = inRange
|
||||
? bindings.buffers[StartSlot + i].buffer.ref()
|
||||
: nullptr;
|
||||
}
|
||||
|
||||
if (pFirstConstant) {
|
||||
pFirstConstant[i] = inRange
|
||||
? bindings.buffers[StartSlot + i].constantOffset
|
||||
: 0u;
|
||||
}
|
||||
|
||||
if (pNumConstants) {
|
||||
pNumConstants[i] = inRange
|
||||
? bindings.buffers[StartSlot + i].constantCount
|
||||
: 0u;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void D3D11CommonContext<ContextType>::GetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView** ppShaderResourceViews) {
|
||||
const auto& bindings = m_state.srv[ShaderStage];
|
||||
|
||||
for (uint32_t i = 0; i < NumViews; i++) {
|
||||
ppShaderResourceViews[i] = StartSlot + i < bindings.views.size()
|
||||
? bindings.views[StartSlot + i].ref()
|
||||
: nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void D3D11CommonContext<ContextType>::GetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState** ppSamplers) {
|
||||
const auto& bindings = m_state.samplers[ShaderStage];
|
||||
|
||||
for (uint32_t i = 0; i < NumSamplers; i++) {
|
||||
ppSamplers[i] = StartSlot + i < bindings.samplers.size()
|
||||
? ref(bindings.samplers[StartSlot + i])
|
||||
: nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
DxvkGlobalPipelineBarrier D3D11CommonContext<ContextType>::GetTiledResourceDependency(
|
||||
ID3D11DeviceChild* pObject) {
|
||||
if (!pObject) {
|
||||
DxvkGlobalPipelineBarrier result;
|
||||
result.stages = VK_PIPELINE_STAGE_ALL_COMMANDS_BIT;
|
||||
result.access = VK_ACCESS_MEMORY_WRITE_BIT | VK_ACCESS_MEMORY_READ_BIT;
|
||||
return result;
|
||||
} else {
|
||||
Com<ID3D11Resource> resource;
|
||||
|
||||
if (FAILED(pObject->QueryInterface(IID_PPV_ARGS(&resource)))) {
|
||||
Com<ID3D11View> view;
|
||||
|
||||
if (FAILED(pObject->QueryInterface(IID_PPV_ARGS(&view))))
|
||||
return DxvkGlobalPipelineBarrier();
|
||||
|
||||
view->GetResource(&resource);
|
||||
}
|
||||
|
||||
D3D11CommonTexture* texture = GetCommonTexture(resource.ptr());
|
||||
|
||||
if (texture) {
|
||||
Rc<DxvkImage> image = texture->GetImage();
|
||||
|
||||
DxvkGlobalPipelineBarrier result;
|
||||
result.stages = image->info().stages;
|
||||
result.access = image->info().access;
|
||||
return result;
|
||||
} else {
|
||||
Rc<DxvkBuffer> buffer = static_cast<D3D11Buffer*>(resource.ptr())->GetBuffer();
|
||||
|
||||
if (buffer == nullptr)
|
||||
return DxvkGlobalPipelineBarrier();
|
||||
|
||||
DxvkGlobalPipelineBarrier result;
|
||||
result.stages = buffer->info().stages;
|
||||
result.access = buffer->info().access;
|
||||
return result;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
D3D11MaxUsedBindings D3D11CommonContext<ContextType>::GetMaxUsedBindings() {
|
||||
D3D11MaxUsedBindings result;
|
||||
|
||||
for (uint32_t i = 0; i < result.stages.size(); i++) {
|
||||
auto stage = DxbcProgramType(i);
|
||||
|
||||
result.stages[i].cbvCount = m_state.cbv[stage].maxCount;
|
||||
result.stages[i].srvCount = m_state.srv[stage].maxCount;
|
||||
result.stages[i].uavCount = 0;
|
||||
result.stages[i].samplerCount = m_state.samplers[stage].maxCount;
|
||||
result.stages[i].reserved = 0;
|
||||
}
|
||||
|
||||
result.stages[uint32_t(DxbcProgramType::PixelShader)].uavCount = m_state.om.maxUav;
|
||||
result.stages[uint32_t(DxbcProgramType::ComputeShader)].uavCount = m_state.uav.maxCount;
|
||||
|
||||
result.vbCount = m_state.ia.maxVbCount;
|
||||
result.soCount = D3D11_SO_BUFFER_SLOT_COUNT;
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::ResetCommandListState() {
|
||||
EmitCs([
|
||||
cUsedBindings = GetMaxUsedBindings()
|
||||
] (DxvkContext* ctx) {
|
||||
// Reset render targets
|
||||
ctx->bindRenderTargets(DxvkRenderTargets(), 0u);
|
||||
|
||||
// Reset vertex input state
|
||||
ctx->setInputLayout(0, nullptr, 0, nullptr);
|
||||
|
||||
// Reset render states
|
||||
DxvkInputAssemblyState iaState;
|
||||
InitDefaultPrimitiveTopology(&iaState);
|
||||
|
||||
DxvkDepthStencilState dsState;
|
||||
InitDefaultDepthStencilState(&dsState);
|
||||
|
||||
DxvkRasterizerState rsState;
|
||||
InitDefaultRasterizerState(&rsState);
|
||||
|
||||
DxvkBlendMode cbState;
|
||||
DxvkLogicOpState loState;
|
||||
DxvkMultisampleState msState;
|
||||
InitDefaultBlendState(&cbState, &loState, &msState, D3D11_DEFAULT_SAMPLE_MASK);
|
||||
|
||||
ctx->setInputAssemblyState(iaState);
|
||||
ctx->setDepthStencilState(dsState);
|
||||
ctx->setRasterizerState(rsState);
|
||||
ctx->setLogicOpState(loState);
|
||||
ctx->setMultisampleState(msState);
|
||||
|
||||
for (uint32_t i = 0; i < D3D11_SIMULTANEOUS_RENDER_TARGET_COUNT; i++)
|
||||
ctx->setBlendMode(i, cbState);
|
||||
|
||||
// Reset dynamic states
|
||||
ctx->setBlendConstants(DxvkBlendConstants { 1.0f, 1.0f, 1.0f, 1.0f });
|
||||
ctx->setStencilReference(D3D11_DEFAULT_STENCIL_REFERENCE);
|
||||
|
||||
// Reset viewports
|
||||
auto viewport = VkViewport();
|
||||
auto scissor = VkRect2D();
|
||||
|
||||
ctx->setViewports(1, &viewport, &scissor);
|
||||
|
||||
// Unbind indirect draw buffer
|
||||
ctx->bindDrawBuffers(DxvkBufferSlice(), DxvkBufferSlice());
|
||||
|
||||
// Unbind index and vertex buffers
|
||||
ctx->bindIndexBuffer(DxvkBufferSlice(), VK_INDEX_TYPE_UINT32);
|
||||
|
||||
for (uint32_t i = 0; i < cUsedBindings.vbCount; i++)
|
||||
ctx->bindVertexBuffer(i, DxvkBufferSlice(), 0);
|
||||
|
||||
// Unbind transform feedback buffers
|
||||
for (uint32_t i = 0; i < cUsedBindings.soCount; i++)
|
||||
ctx->bindXfbBuffer(i, DxvkBufferSlice(), DxvkBufferSlice());
|
||||
|
||||
// Unbind all shaders
|
||||
ctx->bindShader<VK_SHADER_STAGE_VERTEX_BIT>(nullptr);
|
||||
ctx->bindShader<VK_SHADER_STAGE_TESSELLATION_CONTROL_BIT>(nullptr);
|
||||
ctx->bindShader<VK_SHADER_STAGE_TESSELLATION_EVALUATION_BIT>(nullptr);
|
||||
ctx->bindShader<VK_SHADER_STAGE_GEOMETRY_BIT>(nullptr);
|
||||
ctx->bindShader<VK_SHADER_STAGE_FRAGMENT_BIT>(nullptr);
|
||||
ctx->bindShader<VK_SHADER_STAGE_COMPUTE_BIT>(nullptr);
|
||||
|
||||
// Unbind per-shader stage resources
|
||||
for (uint32_t i = 0; i < 6; i++) {
|
||||
auto programType = DxbcProgramType(i);
|
||||
auto stage = GetShaderStage(programType);
|
||||
|
||||
// Unbind constant buffers, including the shader's ICB
|
||||
auto cbSlotId = computeConstantBufferBinding(programType, 0);
|
||||
ctx->bindUniformBuffer(stage, cbSlotId + D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT, DxvkBufferSlice());
|
||||
|
||||
for (uint32_t j = 0; j < cUsedBindings.stages[i].cbvCount; j++)
|
||||
ctx->bindUniformBuffer(stage, cbSlotId + j, DxvkBufferSlice());
|
||||
|
||||
// Unbind shader resource views
|
||||
auto srvSlotId = computeSrvBinding(programType, 0);
|
||||
|
||||
for (uint32_t j = 0; j < cUsedBindings.stages[i].srvCount; j++)
|
||||
ctx->bindResourceImageView(stage, srvSlotId + j, nullptr);
|
||||
|
||||
// Unbind texture samplers
|
||||
auto samplerSlotId = computeSamplerBinding(programType, 0);
|
||||
|
||||
for (uint32_t j = 0; j < cUsedBindings.stages[i].samplerCount; j++)
|
||||
ctx->bindResourceSampler(stage, samplerSlotId + j, nullptr);
|
||||
|
||||
// Unbind UAVs for supported stages
|
||||
if (programType == DxbcProgramType::PixelShader
|
||||
|| programType == DxbcProgramType::ComputeShader) {
|
||||
VkShaderStageFlags stages = programType == DxbcProgramType::PixelShader
|
||||
? VK_SHADER_STAGE_ALL_GRAPHICS
|
||||
: VK_SHADER_STAGE_COMPUTE_BIT;
|
||||
|
||||
auto uavSlotId = computeUavBinding(programType, 0);
|
||||
auto ctrSlotId = computeUavCounterBinding(programType, 0);
|
||||
|
||||
for (uint32_t j = 0; j < cUsedBindings.stages[i].uavCount; j++) {
|
||||
ctx->bindResourceImageView(stages, uavSlotId, nullptr);
|
||||
ctx->bindResourceBufferView(stages, ctrSlotId, nullptr);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Initialize push constants
|
||||
DxbcPushConstants pc;
|
||||
pc.rasterizerSampleCount = 1;
|
||||
ctx->pushConstants(0, sizeof(pc), &pc);
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::ResetContextState() {
|
||||
// Reset shaders
|
||||
m_state.vs = nullptr;
|
||||
m_state.hs = nullptr;
|
||||
m_state.ds = nullptr;
|
||||
m_state.gs = nullptr;
|
||||
m_state.ps = nullptr;
|
||||
m_state.cs = nullptr;
|
||||
|
||||
// Reset render state
|
||||
m_state.id.reset();
|
||||
m_state.ia.reset();
|
||||
m_state.om.reset();
|
||||
m_state.rs.reset();
|
||||
m_state.so.reset();
|
||||
m_state.pr.reset();
|
||||
|
||||
// Reset resource bindings
|
||||
m_state.cbv.reset();
|
||||
m_state.srv.reset();
|
||||
m_state.uav.reset();
|
||||
m_state.samplers.reset();
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::ResetStagingBuffer() {
|
||||
m_staging.reset();
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
template<DxbcProgramType ShaderStage, typename T>
|
||||
void D3D11CommonContext<ContextType>::ResolveSrvHazards(
|
||||
T* pView) {
|
||||
auto& bindings = m_state.srv[ShaderStage];
|
||||
|
||||
uint32_t slotId = computeSrvBinding(ShaderStage, 0);
|
||||
int32_t srvId = bindings.hazardous.findNext(0);
|
||||
|
||||
while (srvId >= 0) {
|
||||
auto srv = bindings.views[srvId].ptr();
|
||||
|
||||
if (likely(srv && srv->TestHazards())) {
|
||||
bool hazard = CheckViewOverlap(pView, srv);
|
||||
|
||||
if (unlikely(hazard)) {
|
||||
bindings.views[srvId] = nullptr;
|
||||
bindings.hazardous.clr(srvId);
|
||||
|
||||
BindShaderResource<ShaderStage>(slotId + srvId, nullptr);
|
||||
}
|
||||
} else {
|
||||
// Avoid further redundant iterations
|
||||
bindings.hazardous.clr(srvId);
|
||||
}
|
||||
|
||||
srvId = bindings.hazardous.findNext(srvId + 1);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
template<typename T>
|
||||
void D3D11CommonContext<ContextType>::ResolveCsSrvHazards(
|
||||
T* pView) {
|
||||
if (!pView) return;
|
||||
ResolveSrvHazards<DxbcProgramType::ComputeShader>(pView);
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
template<typename T>
|
||||
void D3D11CommonContext<ContextType>::ResolveOmSrvHazards(
|
||||
T* pView) {
|
||||
if (!pView) return;
|
||||
ResolveSrvHazards<DxbcProgramType::VertexShader>(pView);
|
||||
ResolveSrvHazards<DxbcProgramType::HullShader>(pView);
|
||||
ResolveSrvHazards<DxbcProgramType::DomainShader>(pView);
|
||||
ResolveSrvHazards<DxbcProgramType::GeometryShader>(pView);
|
||||
ResolveSrvHazards<DxbcProgramType::PixelShader>(pView);
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
bool D3D11CommonContext<ContextType>::ResolveOmRtvHazards(
|
||||
D3D11UnorderedAccessView* pView) {
|
||||
if (!pView || !pView->HasBindFlag(D3D11_BIND_RENDER_TARGET))
|
||||
return false;
|
||||
|
||||
bool hazard = false;
|
||||
|
||||
if (CheckViewOverlap(pView, m_state.om.dsv.ptr())) {
|
||||
m_state.om.dsv = nullptr;
|
||||
hazard = true;
|
||||
}
|
||||
|
||||
for (uint32_t i = 0; i < m_state.om.maxRtv; i++) {
|
||||
if (CheckViewOverlap(pView, m_state.om.rtvs[i].ptr())) {
|
||||
m_state.om.rtvs[i] = nullptr;
|
||||
hazard = true;
|
||||
}
|
||||
}
|
||||
|
||||
return hazard;
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::ResolveOmUavHazards(
|
||||
D3D11RenderTargetView* pView) {
|
||||
if (!pView || !pView->HasBindFlag(D3D11_BIND_UNORDERED_ACCESS))
|
||||
return;
|
||||
|
||||
uint32_t uavSlotId = computeUavBinding (DxbcProgramType::PixelShader, 0);
|
||||
uint32_t ctrSlotId = computeUavCounterBinding(DxbcProgramType::PixelShader, 0);
|
||||
|
||||
for (uint32_t i = 0; i < m_state.om.maxUav; i++) {
|
||||
if (CheckViewOverlap(pView, m_state.om.uavs[i].ptr())) {
|
||||
m_state.om.uavs[i] = nullptr;
|
||||
|
||||
BindUnorderedAccessView<DxbcProgramType::PixelShader>(
|
||||
uavSlotId + i, nullptr,
|
||||
ctrSlotId + i, ~0u);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::RestoreCommandListState() {
|
||||
BindFramebuffer();
|
||||
|
||||
BindShader<DxbcProgramType::VertexShader>(GetCommonShader(m_state.vs.ptr()));
|
||||
BindShader<DxbcProgramType::HullShader>(GetCommonShader(m_state.hs.ptr()));
|
||||
BindShader<DxbcProgramType::DomainShader>(GetCommonShader(m_state.ds.ptr()));
|
||||
BindShader<DxbcProgramType::GeometryShader>(GetCommonShader(m_state.gs.ptr()));
|
||||
BindShader<DxbcProgramType::PixelShader>(GetCommonShader(m_state.ps.ptr()));
|
||||
BindShader<DxbcProgramType::ComputeShader>(GetCommonShader(m_state.cs.ptr()));
|
||||
|
||||
ApplyInputLayout();
|
||||
ApplyPrimitiveTopology();
|
||||
ApplyBlendState();
|
||||
ApplyBlendFactor();
|
||||
ApplyDepthStencilState();
|
||||
ApplyStencilRef();
|
||||
ApplyRasterizerState();
|
||||
ApplyRasterizerSampleCount();
|
||||
ApplyViewportState();
|
||||
|
||||
BindDrawBuffers(
|
||||
m_state.id.argBuffer.ptr(),
|
||||
m_state.id.cntBuffer.ptr());
|
||||
|
||||
BindIndexBuffer(
|
||||
m_state.ia.indexBuffer.buffer.ptr(),
|
||||
m_state.ia.indexBuffer.offset,
|
||||
m_state.ia.indexBuffer.format);
|
||||
|
||||
for (uint32_t i = 0; i < m_state.ia.maxVbCount; i++) {
|
||||
BindVertexBuffer(i,
|
||||
m_state.ia.vertexBuffers[i].buffer.ptr(),
|
||||
m_state.ia.vertexBuffers[i].offset,
|
||||
m_state.ia.vertexBuffers[i].stride);
|
||||
}
|
||||
|
||||
for (uint32_t i = 0; i < m_state.so.targets.size(); i++)
|
||||
BindXfbBuffer(i, m_state.so.targets[i].buffer.ptr(), ~0u);
|
||||
|
||||
RestoreConstantBuffers<DxbcProgramType::VertexShader>();
|
||||
RestoreConstantBuffers<DxbcProgramType::HullShader>();
|
||||
RestoreConstantBuffers<DxbcProgramType::DomainShader>();
|
||||
RestoreConstantBuffers<DxbcProgramType::GeometryShader>();
|
||||
RestoreConstantBuffers<DxbcProgramType::PixelShader>();
|
||||
RestoreConstantBuffers<DxbcProgramType::ComputeShader>();
|
||||
|
||||
RestoreShaderResources<DxbcProgramType::VertexShader>();
|
||||
RestoreShaderResources<DxbcProgramType::HullShader>();
|
||||
RestoreShaderResources<DxbcProgramType::DomainShader>();
|
||||
RestoreShaderResources<DxbcProgramType::GeometryShader>();
|
||||
RestoreShaderResources<DxbcProgramType::PixelShader>();
|
||||
RestoreShaderResources<DxbcProgramType::ComputeShader>();
|
||||
|
||||
RestoreUnorderedAccessViews<DxbcProgramType::PixelShader>();
|
||||
RestoreUnorderedAccessViews<DxbcProgramType::ComputeShader>();
|
||||
|
||||
RestoreSamplers<DxbcProgramType::VertexShader>();
|
||||
RestoreSamplers<DxbcProgramType::HullShader>();
|
||||
RestoreSamplers<DxbcProgramType::DomainShader>();
|
||||
RestoreSamplers<DxbcProgramType::GeometryShader>();
|
||||
RestoreSamplers<DxbcProgramType::PixelShader>();
|
||||
RestoreSamplers<DxbcProgramType::ComputeShader>();
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
template<DxbcProgramType Stage>
|
||||
void D3D11CommonContext<ContextType>::RestoreConstantBuffers() {
|
||||
const auto& bindings = m_state.cbv[Stage];
|
||||
uint32_t slotId = computeConstantBufferBinding(Stage, 0);
|
||||
|
||||
for (uint32_t i = 0; i < bindings.maxCount; i++) {
|
||||
BindConstantBuffer<Stage>(slotId + i, bindings.buffers[i].buffer.ptr(),
|
||||
bindings.buffers[i].constantOffset, bindings.buffers[i].constantBound);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
template<DxbcProgramType Stage>
|
||||
void D3D11CommonContext<ContextType>::RestoreSamplers() {
|
||||
const auto& bindings = m_state.samplers[Stage];
|
||||
uint32_t slotId = computeSamplerBinding(Stage, 0);
|
||||
|
||||
for (uint32_t i = 0; i < bindings.maxCount; i++)
|
||||
BindSampler<Stage>(slotId + i, bindings.samplers[i]);
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
template<DxbcProgramType Stage>
|
||||
void D3D11CommonContext<ContextType>::RestoreShaderResources() {
|
||||
const auto& bindings = m_state.srv[Stage];
|
||||
uint32_t slotId = computeSrvBinding(Stage, 0);
|
||||
|
||||
for (uint32_t i = 0; i < bindings.maxCount; i++)
|
||||
BindShaderResource<Stage>(slotId + i, bindings.views[i].ptr());
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
template<DxbcProgramType Stage>
|
||||
void D3D11CommonContext<ContextType>::RestoreUnorderedAccessViews() {
|
||||
const auto& views = Stage == DxbcProgramType::ComputeShader
|
||||
? m_state.uav.views
|
||||
: m_state.om.uavs;
|
||||
|
||||
uint32_t maxCount = Stage == DxbcProgramType::ComputeShader
|
||||
? m_state.uav.maxCount
|
||||
: m_state.om.maxUav;
|
||||
|
||||
uint32_t uavSlotId = computeUavBinding(Stage, 0);
|
||||
uint32_t ctrSlotId = computeUavCounterBinding(Stage, 0);
|
||||
|
||||
for (uint32_t i = 0; i < maxCount; i++) {
|
||||
BindUnorderedAccessView<Stage>(
|
||||
uavSlotId + i, views[i].ptr(),
|
||||
ctrSlotId + i, ~0u);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void D3D11CommonContext<ContextType>::SetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers) {
|
||||
auto& bindings = m_state.cbv[ShaderStage];
|
||||
uint32_t slotId = computeConstantBufferBinding(ShaderStage, StartSlot);
|
||||
|
||||
for (uint32_t i = 0; i < NumBuffers; i++) {
|
||||
auto newBuffer = static_cast<D3D11Buffer*>(ppConstantBuffers[i]);
|
||||
|
||||
uint32_t constantCount = newBuffer
|
||||
? std::min(newBuffer->Desc()->ByteWidth / 16, UINT(D3D11_REQ_CONSTANT_BUFFER_ELEMENT_COUNT))
|
||||
: 0u;
|
||||
|
||||
if (bindings.buffers[StartSlot + i].buffer != newBuffer
|
||||
|| bindings.buffers[StartSlot + i].constantOffset != 0
|
||||
|| bindings.buffers[StartSlot + i].constantCount != constantCount) {
|
||||
bindings.buffers[StartSlot + i].buffer = newBuffer;
|
||||
bindings.buffers[StartSlot + i].constantOffset = 0;
|
||||
bindings.buffers[StartSlot + i].constantCount = constantCount;
|
||||
bindings.buffers[StartSlot + i].constantBound = constantCount;
|
||||
|
||||
BindConstantBuffer<ShaderStage>(slotId + i, newBuffer, 0, constantCount);
|
||||
}
|
||||
}
|
||||
|
||||
bindings.maxCount = std::clamp(StartSlot + NumBuffers,
|
||||
bindings.maxCount, uint32_t(bindings.buffers.size()));
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void D3D11CommonContext<ContextType>::SetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers,
|
||||
const UINT* pFirstConstant,
|
||||
const UINT* pNumConstants) {
|
||||
auto& bindings = m_state.cbv[ShaderStage];
|
||||
|
||||
uint32_t slotId = computeConstantBufferBinding(ShaderStage, StartSlot);
|
||||
|
||||
for (uint32_t i = 0; i < NumBuffers; i++) {
|
||||
auto newBuffer = static_cast<D3D11Buffer*>(ppConstantBuffers[i]);
|
||||
|
||||
UINT constantOffset;
|
||||
UINT constantCount;
|
||||
UINT constantBound;
|
||||
|
||||
if (likely(newBuffer != nullptr)) {
|
||||
UINT bufferConstantsCount = newBuffer->Desc()->ByteWidth / 16;
|
||||
constantBound = std::min(bufferConstantsCount, UINT(D3D11_REQ_CONSTANT_BUFFER_ELEMENT_COUNT));
|
||||
|
||||
if (likely(pFirstConstant && pNumConstants)) {
|
||||
constantOffset = pFirstConstant[i];
|
||||
constantCount = pNumConstants [i];
|
||||
|
||||
if (unlikely(constantCount > D3D11_REQ_CONSTANT_BUFFER_ELEMENT_COUNT))
|
||||
continue;
|
||||
|
||||
constantBound = (constantOffset + constantCount > bufferConstantsCount)
|
||||
? bufferConstantsCount - std::min(constantOffset, bufferConstantsCount)
|
||||
: constantCount;
|
||||
} else {
|
||||
constantOffset = 0;
|
||||
constantCount = constantBound;
|
||||
}
|
||||
} else {
|
||||
constantOffset = 0;
|
||||
constantCount = 0;
|
||||
constantBound = 0;
|
||||
}
|
||||
|
||||
// Do a full rebind if either the buffer changes
|
||||
if (bindings.buffers[StartSlot + i].buffer != newBuffer) {
|
||||
bindings.buffers[StartSlot + i].buffer = newBuffer;
|
||||
bindings.buffers[StartSlot + i].constantOffset = constantOffset;
|
||||
bindings.buffers[StartSlot + i].constantCount = constantCount;
|
||||
bindings.buffers[StartSlot + i].constantBound = constantBound;
|
||||
|
||||
BindConstantBuffer<ShaderStage>(slotId + i, newBuffer, constantOffset, constantBound);
|
||||
} else if (bindings.buffers[StartSlot + i].constantOffset != constantOffset
|
||||
|| bindings.buffers[StartSlot + i].constantCount != constantCount) {
|
||||
bindings.buffers[StartSlot + i].constantOffset = constantOffset;
|
||||
bindings.buffers[StartSlot + i].constantCount = constantCount;
|
||||
bindings.buffers[StartSlot + i].constantBound = constantBound;
|
||||
|
||||
BindConstantBufferRange<ShaderStage>(slotId + i, constantOffset, constantBound);
|
||||
}
|
||||
}
|
||||
|
||||
bindings.maxCount = std::clamp(StartSlot + NumBuffers,
|
||||
bindings.maxCount, uint32_t(bindings.buffers.size()));
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void D3D11CommonContext<ContextType>::SetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumResources,
|
||||
ID3D11ShaderResourceView* const* ppResources) {
|
||||
auto& bindings = m_state.srv[ShaderStage];
|
||||
uint32_t slotId = computeSrvBinding(ShaderStage, StartSlot);
|
||||
|
||||
for (uint32_t i = 0; i < NumResources; i++) {
|
||||
auto resView = static_cast<D3D11ShaderResourceView*>(ppResources[i]);
|
||||
|
||||
if (bindings.views[StartSlot + i] != resView) {
|
||||
if (likely(resView != nullptr)) {
|
||||
if (unlikely(resView->TestHazards())) {
|
||||
if (TestSrvHazards<ShaderStage>(resView))
|
||||
resView = nullptr;
|
||||
|
||||
// Only set if necessary, but don't reset it on every
|
||||
// bind as this would be more expensive than a few
|
||||
// redundant checks in OMSetRenderTargets and friends.
|
||||
bindings.hazardous.set(StartSlot + i, resView);
|
||||
}
|
||||
}
|
||||
|
||||
bindings.views[StartSlot + i] = resView;
|
||||
BindShaderResource<ShaderStage>(slotId + i, resView);
|
||||
}
|
||||
}
|
||||
|
||||
bindings.maxCount = std::clamp(StartSlot + NumResources,
|
||||
bindings.maxCount, uint32_t(bindings.views.size()));
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void D3D11CommonContext<ContextType>::SetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState* const* ppSamplers) {
|
||||
auto& bindings = m_state.samplers[ShaderStage];
|
||||
uint32_t slotId = computeSamplerBinding(ShaderStage, StartSlot);
|
||||
|
||||
for (uint32_t i = 0; i < NumSamplers; i++) {
|
||||
auto sampler = static_cast<D3D11SamplerState*>(ppSamplers[i]);
|
||||
|
||||
if (bindings.samplers[StartSlot + i] != sampler) {
|
||||
bindings.samplers[StartSlot + i] = sampler;
|
||||
BindSampler<ShaderStage>(slotId + i, sampler);
|
||||
}
|
||||
}
|
||||
|
||||
bindings.maxCount = std::clamp(StartSlot + NumSamplers,
|
||||
bindings.maxCount, uint32_t(bindings.samplers.size()));
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::SetRenderTargetsAndUnorderedAccessViews(
|
||||
UINT NumRTVs,
|
||||
ID3D11RenderTargetView* const* ppRenderTargetViews,
|
||||
ID3D11DepthStencilView* pDepthStencilView,
|
||||
UINT UAVStartSlot,
|
||||
UINT NumUAVs,
|
||||
ID3D11UnorderedAccessView* const* ppUnorderedAccessViews,
|
||||
const UINT* pUAVInitialCounts) {
|
||||
if (TestRtvUavHazards(NumRTVs, ppRenderTargetViews, NumUAVs, ppUnorderedAccessViews))
|
||||
return;
|
||||
|
||||
bool needsUpdate = false;
|
||||
|
||||
if (likely(NumRTVs != D3D11_KEEP_RENDER_TARGETS_AND_DEPTH_STENCIL)) {
|
||||
// Native D3D11 does not change the render targets if
|
||||
// the parameters passed to this method are invalid.
|
||||
if (!ValidateRenderTargets(NumRTVs, ppRenderTargetViews, pDepthStencilView))
|
||||
return;
|
||||
|
||||
for (uint32_t i = 0; i < m_state.om.rtvs.size(); i++) {
|
||||
auto rtv = i < NumRTVs
|
||||
? static_cast<D3D11RenderTargetView*>(ppRenderTargetViews[i])
|
||||
: nullptr;
|
||||
|
||||
if (m_state.om.rtvs[i] != rtv) {
|
||||
m_state.om.rtvs[i] = rtv;
|
||||
needsUpdate = true;
|
||||
ResolveOmSrvHazards(rtv);
|
||||
|
||||
if (NumUAVs == D3D11_KEEP_UNORDERED_ACCESS_VIEWS)
|
||||
ResolveOmUavHazards(rtv);
|
||||
}
|
||||
}
|
||||
|
||||
auto dsv = static_cast<D3D11DepthStencilView*>(pDepthStencilView);
|
||||
|
||||
if (m_state.om.dsv != dsv) {
|
||||
m_state.om.dsv = dsv;
|
||||
needsUpdate = true;
|
||||
ResolveOmSrvHazards(dsv);
|
||||
}
|
||||
|
||||
m_state.om.maxRtv = NumRTVs;
|
||||
}
|
||||
|
||||
if (unlikely(NumUAVs || m_state.om.maxUav)) {
|
||||
uint32_t uavSlotId = computeUavBinding (DxbcProgramType::PixelShader, 0);
|
||||
uint32_t ctrSlotId = computeUavCounterBinding(DxbcProgramType::PixelShader, 0);
|
||||
|
||||
if (likely(NumUAVs != D3D11_KEEP_UNORDERED_ACCESS_VIEWS)) {
|
||||
uint32_t newMaxUav = NumUAVs ? UAVStartSlot + NumUAVs : 0;
|
||||
uint32_t oldMaxUav = std::exchange(m_state.om.maxUav, newMaxUav);
|
||||
|
||||
for (uint32_t i = 0; i < std::max(oldMaxUav, newMaxUav); i++) {
|
||||
D3D11UnorderedAccessView* uav = nullptr;
|
||||
uint32_t ctr = ~0u;
|
||||
|
||||
if (i >= UAVStartSlot && i < UAVStartSlot + NumUAVs) {
|
||||
uav = static_cast<D3D11UnorderedAccessView*>(ppUnorderedAccessViews[i - UAVStartSlot]);
|
||||
ctr = pUAVInitialCounts ? pUAVInitialCounts[i - UAVStartSlot] : ~0u;
|
||||
}
|
||||
|
||||
if (m_state.om.uavs[i] != uav || ctr != ~0u) {
|
||||
m_state.om.uavs[i] = uav;
|
||||
|
||||
BindUnorderedAccessView<DxbcProgramType::PixelShader>(
|
||||
uavSlotId + i, uav,
|
||||
ctrSlotId + i, ctr);
|
||||
|
||||
ResolveOmSrvHazards(uav);
|
||||
|
||||
if (NumRTVs == D3D11_KEEP_RENDER_TARGETS_AND_DEPTH_STENCIL)
|
||||
needsUpdate |= ResolveOmRtvHazards(uav);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (needsUpdate) {
|
||||
BindFramebuffer();
|
||||
|
||||
if constexpr (!IsDeferred) {
|
||||
// Doing this makes it less likely to flush during render passes
|
||||
GetTypedContext()->ConsiderFlush(GpuFlushType::ImplicitWeakHint);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::SetDrawBuffers(
|
||||
ID3D11Buffer* pBufferForArgs,
|
||||
ID3D11Buffer* pBufferForCount) {
|
||||
auto argBuffer = static_cast<D3D11Buffer*>(pBufferForArgs);
|
||||
auto cntBuffer = static_cast<D3D11Buffer*>(pBufferForCount);
|
||||
|
||||
if (m_state.id.argBuffer != argBuffer
|
||||
|| m_state.id.cntBuffer != cntBuffer) {
|
||||
m_state.id.argBuffer = argBuffer;
|
||||
m_state.id.cntBuffer = cntBuffer;
|
||||
|
||||
BindDrawBuffers(argBuffer, cntBuffer);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
bool D3D11CommonContext<ContextType>::TestRtvUavHazards(
|
||||
UINT NumRTVs,
|
||||
ID3D11RenderTargetView* const* ppRTVs,
|
||||
UINT NumUAVs,
|
||||
ID3D11UnorderedAccessView* const* ppUAVs) {
|
||||
if (NumRTVs == D3D11_KEEP_RENDER_TARGETS_AND_DEPTH_STENCIL) NumRTVs = 0;
|
||||
if (NumUAVs == D3D11_KEEP_UNORDERED_ACCESS_VIEWS) NumUAVs = 0;
|
||||
|
||||
for (uint32_t i = 0; i < NumRTVs; i++) {
|
||||
auto rtv = static_cast<D3D11RenderTargetView*>(ppRTVs[i]);
|
||||
|
||||
if (!rtv)
|
||||
continue;
|
||||
|
||||
for (uint32_t j = 0; j < i; j++) {
|
||||
if (CheckViewOverlap(rtv, static_cast<D3D11RenderTargetView*>(ppRTVs[j])))
|
||||
return true;
|
||||
}
|
||||
|
||||
if (rtv->HasBindFlag(D3D11_BIND_UNORDERED_ACCESS)) {
|
||||
for (uint32_t j = 0; j < NumUAVs; j++) {
|
||||
if (CheckViewOverlap(rtv, static_cast<D3D11UnorderedAccessView*>(ppUAVs[j])))
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for (uint32_t i = 0; i < NumUAVs; i++) {
|
||||
auto uav = static_cast<D3D11UnorderedAccessView*>(ppUAVs[i]);
|
||||
|
||||
if (!uav)
|
||||
continue;
|
||||
|
||||
for (uint32_t j = 0; j < i; j++) {
|
||||
if (CheckViewOverlap(uav, static_cast<D3D11UnorderedAccessView*>(ppUAVs[j])))
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
template<DxbcProgramType ShaderStage>
|
||||
bool D3D11CommonContext<ContextType>::TestSrvHazards(
|
||||
D3D11ShaderResourceView* pView) {
|
||||
bool hazard = false;
|
||||
|
||||
if (ShaderStage == DxbcProgramType::ComputeShader) {
|
||||
int32_t uav = m_state.uav.mask.findNext(0);
|
||||
|
||||
while (uav >= 0 && !hazard) {
|
||||
hazard = CheckViewOverlap(pView, m_state.uav.views[uav].ptr());
|
||||
uav = m_state.uav.mask.findNext(uav + 1);
|
||||
}
|
||||
} else {
|
||||
hazard = CheckViewOverlap(pView, m_state.om.dsv.ptr());
|
||||
|
||||
for (uint32_t i = 0; !hazard && i < m_state.om.maxRtv; i++)
|
||||
hazard = CheckViewOverlap(pView, m_state.om.rtvs[i].ptr());
|
||||
|
||||
for (uint32_t i = 0; !hazard && i < m_state.om.maxUav; i++)
|
||||
hazard = CheckViewOverlap(pView, m_state.om.uavs[i].ptr());
|
||||
}
|
||||
|
||||
return hazard;
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::TrackResourceSequenceNumber(
|
||||
ID3D11Resource* pResource) {
|
||||
if (!pResource)
|
||||
return;
|
||||
|
||||
D3D11CommonTexture* texture = GetCommonTexture(pResource);
|
||||
|
||||
if (texture) {
|
||||
if (texture->HasSequenceNumber()) {
|
||||
for (uint32_t i = 0; i < texture->CountSubresources(); i++)
|
||||
GetTypedContext()->TrackTextureSequenceNumber(texture, i);
|
||||
}
|
||||
} else {
|
||||
D3D11Buffer* buffer = static_cast<D3D11Buffer*>(pResource);
|
||||
|
||||
if (buffer->HasSequenceNumber())
|
||||
GetTypedContext()->TrackBufferSequenceNumber(buffer);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::UpdateBuffer(
|
||||
D3D11Buffer* pDstBuffer,
|
||||
UINT Offset,
|
||||
UINT Length,
|
||||
@ -3680,11 +5111,12 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
if (pDstBuffer->HasSequenceNumber())
|
||||
TrackBufferSequenceNumber(pDstBuffer);
|
||||
GetTypedContext()->TrackBufferSequenceNumber(pDstBuffer);
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::UpdateTexture(
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::UpdateTexture(
|
||||
D3D11CommonTexture* pDstTexture,
|
||||
UINT DstSubresource,
|
||||
const D3D11_BOX* pDstBox,
|
||||
@ -3696,7 +5128,7 @@ namespace dxvk {
|
||||
|
||||
VkFormat packedFormat = pDstTexture->GetPackedFormat();
|
||||
|
||||
auto formatInfo = imageFormatInfo(packedFormat);
|
||||
auto formatInfo = lookupFormatInfo(packedFormat);
|
||||
auto subresource = pDstTexture->GetSubresourceFromIndex(
|
||||
formatInfo->aspectMask, DstSubresource);
|
||||
|
||||
@ -3720,10 +5152,8 @@ namespace dxvk {
|
||||
extent.depth = pDstBox->back - pDstBox->front;
|
||||
}
|
||||
|
||||
if (!util::isBlockAligned(offset, extent, formatInfo->blockSize, mipExtent)) {
|
||||
Logger::err("D3D11: UpdateSubresource1: Unaligned region");
|
||||
if (!util::isBlockAligned(offset, extent, formatInfo->blockSize, mipExtent))
|
||||
return;
|
||||
}
|
||||
|
||||
auto stagingSlice = AllocStagingBuffer(util::computeImageDataSize(packedFormat, extent));
|
||||
|
||||
@ -3737,7 +5167,8 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::UpdateImage(
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::UpdateImage(
|
||||
D3D11CommonTexture* pDstTexture,
|
||||
const VkImageSubresource* pDstSubresource,
|
||||
VkOffset3D DstOffset,
|
||||
@ -3780,7 +5211,7 @@ namespace dxvk {
|
||||
VkExtent3D dstMipExtent = pDstTexture->MipLevelExtent(pDstSubresource->mipLevel);
|
||||
|
||||
auto dstFormat = pDstTexture->GetPackedFormat();
|
||||
auto dstFormatInfo = imageFormatInfo(dstFormat);
|
||||
auto dstFormatInfo = lookupFormatInfo(dstFormat);
|
||||
|
||||
uint32_t planeCount = 1;
|
||||
|
||||
@ -3828,612 +5259,115 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
if (pDstTexture->HasSequenceNumber())
|
||||
TrackTextureSequenceNumber(pDstTexture, dstSubresource);
|
||||
GetTypedContext()->TrackTextureSequenceNumber(pDstTexture, dstSubresource);
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::SetDrawBuffers(
|
||||
ID3D11Buffer* pBufferForArgs,
|
||||
ID3D11Buffer* pBufferForCount) {
|
||||
auto argBuffer = static_cast<D3D11Buffer*>(pBufferForArgs);
|
||||
auto cntBuffer = static_cast<D3D11Buffer*>(pBufferForCount);
|
||||
|
||||
if (m_state.id.argBuffer != argBuffer
|
||||
|| m_state.id.cntBuffer != cntBuffer) {
|
||||
m_state.id.argBuffer = argBuffer;
|
||||
m_state.id.cntBuffer = cntBuffer;
|
||||
|
||||
BindDrawBuffers(argBuffer, cntBuffer);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void D3D11DeviceContext::SetConstantBuffers(
|
||||
D3D11ConstantBufferBindings& Bindings,
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers) {
|
||||
uint32_t slotId = computeConstantBufferBinding(ShaderStage, StartSlot);
|
||||
|
||||
for (uint32_t i = 0; i < NumBuffers; i++) {
|
||||
auto newBuffer = static_cast<D3D11Buffer*>(ppConstantBuffers[i]);
|
||||
|
||||
UINT constantCount = 0;
|
||||
|
||||
if (likely(newBuffer != nullptr))
|
||||
constantCount = std::min(newBuffer->Desc()->ByteWidth / 16, UINT(D3D11_REQ_CONSTANT_BUFFER_ELEMENT_COUNT));
|
||||
|
||||
if (Bindings[StartSlot + i].buffer != newBuffer
|
||||
|| Bindings[StartSlot + i].constantCount != constantCount) {
|
||||
Bindings[StartSlot + i].buffer = newBuffer;
|
||||
Bindings[StartSlot + i].constantOffset = 0;
|
||||
Bindings[StartSlot + i].constantCount = constantCount;
|
||||
Bindings[StartSlot + i].constantBound = constantCount;
|
||||
|
||||
BindConstantBuffer(slotId + i, newBuffer, 0, constantCount);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void D3D11DeviceContext::SetConstantBuffers1(
|
||||
D3D11ConstantBufferBindings& Bindings,
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers,
|
||||
const UINT* pFirstConstant,
|
||||
const UINT* pNumConstants) {
|
||||
uint32_t slotId = computeConstantBufferBinding(ShaderStage, StartSlot);
|
||||
|
||||
for (uint32_t i = 0; i < NumBuffers; i++) {
|
||||
auto newBuffer = static_cast<D3D11Buffer*>(ppConstantBuffers[i]);
|
||||
|
||||
UINT constantOffset;
|
||||
UINT constantCount;
|
||||
UINT constantBound;
|
||||
|
||||
if (likely(newBuffer != nullptr)) {
|
||||
UINT bufferConstantsCount = newBuffer->Desc()->ByteWidth / 16;
|
||||
constantBound = std::min(bufferConstantsCount, UINT(D3D11_REQ_CONSTANT_BUFFER_ELEMENT_COUNT));
|
||||
|
||||
if (likely(pFirstConstant && pNumConstants)) {
|
||||
constantOffset = pFirstConstant[i];
|
||||
constantCount = pNumConstants [i];
|
||||
|
||||
if (unlikely(constantCount > D3D11_REQ_CONSTANT_BUFFER_ELEMENT_COUNT))
|
||||
continue;
|
||||
|
||||
constantBound = (constantOffset + constantCount > bufferConstantsCount)
|
||||
? bufferConstantsCount - std::min(constantOffset, bufferConstantsCount)
|
||||
: constantCount;
|
||||
} else {
|
||||
constantOffset = 0;
|
||||
constantCount = constantBound;
|
||||
}
|
||||
} else {
|
||||
constantOffset = 0;
|
||||
constantCount = 0;
|
||||
constantBound = 0;
|
||||
}
|
||||
|
||||
bool needsUpdate = Bindings[StartSlot + i].buffer != newBuffer;
|
||||
|
||||
if (needsUpdate)
|
||||
Bindings[StartSlot + i].buffer = newBuffer;
|
||||
|
||||
needsUpdate |= Bindings[StartSlot + i].constantOffset != constantOffset
|
||||
|| Bindings[StartSlot + i].constantCount != constantCount;
|
||||
|
||||
if (needsUpdate) {
|
||||
Bindings[StartSlot + i].constantOffset = constantOffset;
|
||||
Bindings[StartSlot + i].constantCount = constantCount;
|
||||
Bindings[StartSlot + i].constantBound = constantBound;
|
||||
|
||||
BindConstantBuffer(slotId + i, newBuffer, constantOffset, constantBound);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void D3D11DeviceContext::SetSamplers(
|
||||
D3D11SamplerBindings& Bindings,
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState* const* ppSamplers) {
|
||||
uint32_t slotId = computeSamplerBinding(ShaderStage, StartSlot);
|
||||
|
||||
for (uint32_t i = 0; i < NumSamplers; i++) {
|
||||
auto sampler = static_cast<D3D11SamplerState*>(ppSamplers[i]);
|
||||
|
||||
if (Bindings[StartSlot + i] != sampler) {
|
||||
Bindings[StartSlot + i] = sampler;
|
||||
BindSampler(slotId + i, sampler);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void D3D11DeviceContext::SetShaderResources(
|
||||
D3D11ShaderResourceBindings& Bindings,
|
||||
UINT StartSlot,
|
||||
UINT NumResources,
|
||||
ID3D11ShaderResourceView* const* ppResources) {
|
||||
uint32_t slotId = computeSrvBinding(ShaderStage, StartSlot);
|
||||
|
||||
for (uint32_t i = 0; i < NumResources; i++) {
|
||||
auto resView = static_cast<D3D11ShaderResourceView*>(ppResources[i]);
|
||||
|
||||
if (Bindings.views[StartSlot + i] != resView) {
|
||||
if (unlikely(resView && resView->TestHazards())) {
|
||||
if (TestSrvHazards<ShaderStage>(resView))
|
||||
resView = nullptr;
|
||||
|
||||
// Only set if necessary, but don't reset it on every
|
||||
// bind as this would be more expensive than a few
|
||||
// redundant checks in OMSetRenderTargets and friends.
|
||||
Bindings.hazardous.set(StartSlot + i, resView);
|
||||
}
|
||||
|
||||
Bindings.views[StartSlot + i] = resView;
|
||||
BindShaderResource(slotId + i, resView);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::GetConstantBuffers(
|
||||
const D3D11ConstantBufferBindings& Bindings,
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppConstantBuffers,
|
||||
UINT* pFirstConstant,
|
||||
UINT* pNumConstants) {
|
||||
for (uint32_t i = 0; i < NumBuffers; i++) {
|
||||
const bool inRange = StartSlot + i < Bindings.size();
|
||||
|
||||
if (ppConstantBuffers != nullptr) {
|
||||
ppConstantBuffers[i] = inRange
|
||||
? Bindings[StartSlot + i].buffer.ref()
|
||||
: nullptr;
|
||||
}
|
||||
|
||||
if (pFirstConstant != nullptr) {
|
||||
pFirstConstant[i] = inRange
|
||||
? Bindings[StartSlot + i].constantOffset
|
||||
: 0u;
|
||||
}
|
||||
|
||||
if (pNumConstants != nullptr) {
|
||||
pNumConstants[i] = inRange
|
||||
? Bindings[StartSlot + i].constantCount
|
||||
: 0u;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::GetShaderResources(
|
||||
const D3D11ShaderResourceBindings& Bindings,
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView** ppShaderResourceViews) {
|
||||
for (uint32_t i = 0; i < NumViews; i++) {
|
||||
ppShaderResourceViews[i] = StartSlot + i < Bindings.views.size()
|
||||
? Bindings.views[StartSlot + i].ref()
|
||||
: nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::GetSamplers(
|
||||
const D3D11SamplerBindings& Bindings,
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState** ppSamplers) {
|
||||
for (uint32_t i = 0; i < NumSamplers; i++) {
|
||||
ppSamplers[i] = StartSlot + i < Bindings.size()
|
||||
? ref(Bindings[StartSlot + i])
|
||||
: nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::ResetState() {
|
||||
EmitCs([] (DxvkContext* ctx) {
|
||||
// Reset render targets
|
||||
ctx->bindRenderTargets(DxvkRenderTargets());
|
||||
|
||||
// Reset vertex input state
|
||||
ctx->setInputLayout(0, nullptr, 0, nullptr);
|
||||
|
||||
// Reset render states
|
||||
DxvkInputAssemblyState iaState;
|
||||
InitDefaultPrimitiveTopology(&iaState);
|
||||
|
||||
DxvkDepthStencilState dsState;
|
||||
InitDefaultDepthStencilState(&dsState);
|
||||
|
||||
DxvkRasterizerState rsState;
|
||||
InitDefaultRasterizerState(&rsState);
|
||||
|
||||
DxvkBlendMode cbState;
|
||||
DxvkLogicOpState loState;
|
||||
DxvkMultisampleState msState;
|
||||
InitDefaultBlendState(&cbState, &loState, &msState, D3D11_DEFAULT_SAMPLE_MASK);
|
||||
|
||||
ctx->setInputAssemblyState(iaState);
|
||||
ctx->setDepthStencilState(dsState);
|
||||
ctx->setRasterizerState(rsState);
|
||||
ctx->setLogicOpState(loState);
|
||||
ctx->setMultisampleState(msState);
|
||||
|
||||
for (uint32_t i = 0; i < D3D11_SIMULTANEOUS_RENDER_TARGET_COUNT; i++)
|
||||
ctx->setBlendMode(i, cbState);
|
||||
|
||||
// Reset dynamic states
|
||||
ctx->setBlendConstants(DxvkBlendConstants { 1.0f, 1.0f, 1.0f, 1.0f });
|
||||
ctx->setStencilReference(D3D11_DEFAULT_STENCIL_REFERENCE);
|
||||
|
||||
// Reset viewports
|
||||
auto viewport = VkViewport();
|
||||
auto scissor = VkRect2D();
|
||||
|
||||
ctx->setViewports(1, &viewport, &scissor);
|
||||
|
||||
// Unbind indirect draw buffer
|
||||
ctx->bindDrawBuffers(DxvkBufferSlice(), DxvkBufferSlice());
|
||||
|
||||
// Unbind index and vertex buffers
|
||||
ctx->bindIndexBuffer(DxvkBufferSlice(), VK_INDEX_TYPE_UINT32);
|
||||
|
||||
for (uint32_t i = 0; i < D3D11_IA_VERTEX_INPUT_RESOURCE_SLOT_COUNT; i++)
|
||||
ctx->bindVertexBuffer(i, DxvkBufferSlice(), 0);
|
||||
|
||||
// Unbind transform feedback buffers
|
||||
for (uint32_t i = 0; i < D3D11_SO_BUFFER_SLOT_COUNT; i++)
|
||||
ctx->bindXfbBuffer(i, DxvkBufferSlice(), DxvkBufferSlice());
|
||||
|
||||
// Unbind per-shader stage resources
|
||||
for (uint32_t i = 0; i < 6; i++) {
|
||||
auto programType = DxbcProgramType(i);
|
||||
ctx->bindShader(GetShaderStage(programType), nullptr);
|
||||
|
||||
// Unbind constant buffers, including the shader's ICB
|
||||
auto cbSlotId = computeConstantBufferBinding(programType, 0);
|
||||
|
||||
for (uint32_t j = 0; j <= D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT; j++)
|
||||
ctx->bindResourceBuffer(cbSlotId + j, DxvkBufferSlice());
|
||||
|
||||
// Unbind shader resource views
|
||||
auto srvSlotId = computeSrvBinding(programType, 0);
|
||||
|
||||
for (uint32_t j = 0; j < D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT; j++)
|
||||
ctx->bindResourceView(srvSlotId + j, nullptr, nullptr);
|
||||
|
||||
// Unbind texture samplers
|
||||
auto samplerSlotId = computeSamplerBinding(programType, 0);
|
||||
|
||||
for (uint32_t j = 0; j < D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT; j++)
|
||||
ctx->bindResourceSampler(samplerSlotId + j, nullptr);
|
||||
|
||||
// Unbind UAVs for supported stages
|
||||
if (programType == DxbcProgramType::PixelShader
|
||||
|| programType == DxbcProgramType::ComputeShader) {
|
||||
auto uavSlotId = computeUavBinding(programType, 0);
|
||||
auto ctrSlotId = computeUavCounterBinding(programType, 0);
|
||||
|
||||
for (uint32_t j = 0; j < D3D11_1_UAV_SLOT_COUNT; j++) {
|
||||
ctx->bindResourceView (uavSlotId, nullptr, nullptr);
|
||||
ctx->bindResourceBuffer (ctrSlotId, DxvkBufferSlice());
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::RestoreState() {
|
||||
BindFramebuffer();
|
||||
|
||||
BindShader<DxbcProgramType::VertexShader> (GetCommonShader(m_state.vs.shader.ptr()));
|
||||
BindShader<DxbcProgramType::HullShader> (GetCommonShader(m_state.hs.shader.ptr()));
|
||||
BindShader<DxbcProgramType::DomainShader> (GetCommonShader(m_state.ds.shader.ptr()));
|
||||
BindShader<DxbcProgramType::GeometryShader> (GetCommonShader(m_state.gs.shader.ptr()));
|
||||
BindShader<DxbcProgramType::PixelShader> (GetCommonShader(m_state.ps.shader.ptr()));
|
||||
BindShader<DxbcProgramType::ComputeShader> (GetCommonShader(m_state.cs.shader.ptr()));
|
||||
|
||||
ApplyInputLayout();
|
||||
ApplyPrimitiveTopology();
|
||||
ApplyBlendState();
|
||||
ApplyBlendFactor();
|
||||
ApplyDepthStencilState();
|
||||
ApplyStencilRef();
|
||||
ApplyRasterizerState();
|
||||
ApplyViewportState();
|
||||
|
||||
BindDrawBuffers(
|
||||
m_state.id.argBuffer.ptr(),
|
||||
m_state.id.cntBuffer.ptr());
|
||||
|
||||
BindIndexBuffer(
|
||||
m_state.ia.indexBuffer.buffer.ptr(),
|
||||
m_state.ia.indexBuffer.offset,
|
||||
m_state.ia.indexBuffer.format);
|
||||
|
||||
for (uint32_t i = 0; i < m_state.ia.vertexBuffers.size(); i++) {
|
||||
BindVertexBuffer(i,
|
||||
m_state.ia.vertexBuffers[i].buffer.ptr(),
|
||||
m_state.ia.vertexBuffers[i].offset,
|
||||
m_state.ia.vertexBuffers[i].stride);
|
||||
}
|
||||
|
||||
for (uint32_t i = 0; i < m_state.so.targets.size(); i++)
|
||||
BindXfbBuffer(i, m_state.so.targets[i].buffer.ptr(), ~0u);
|
||||
|
||||
RestoreConstantBuffers<DxbcProgramType::VertexShader> (m_state.vs.constantBuffers);
|
||||
RestoreConstantBuffers<DxbcProgramType::HullShader> (m_state.hs.constantBuffers);
|
||||
RestoreConstantBuffers<DxbcProgramType::DomainShader> (m_state.ds.constantBuffers);
|
||||
RestoreConstantBuffers<DxbcProgramType::GeometryShader> (m_state.gs.constantBuffers);
|
||||
RestoreConstantBuffers<DxbcProgramType::PixelShader> (m_state.ps.constantBuffers);
|
||||
RestoreConstantBuffers<DxbcProgramType::ComputeShader> (m_state.cs.constantBuffers);
|
||||
|
||||
RestoreSamplers<DxbcProgramType::VertexShader> (m_state.vs.samplers);
|
||||
RestoreSamplers<DxbcProgramType::HullShader> (m_state.hs.samplers);
|
||||
RestoreSamplers<DxbcProgramType::DomainShader> (m_state.ds.samplers);
|
||||
RestoreSamplers<DxbcProgramType::GeometryShader>(m_state.gs.samplers);
|
||||
RestoreSamplers<DxbcProgramType::PixelShader> (m_state.ps.samplers);
|
||||
RestoreSamplers<DxbcProgramType::ComputeShader> (m_state.cs.samplers);
|
||||
|
||||
RestoreShaderResources<DxbcProgramType::VertexShader> (m_state.vs.shaderResources);
|
||||
RestoreShaderResources<DxbcProgramType::HullShader> (m_state.hs.shaderResources);
|
||||
RestoreShaderResources<DxbcProgramType::DomainShader> (m_state.ds.shaderResources);
|
||||
RestoreShaderResources<DxbcProgramType::GeometryShader> (m_state.gs.shaderResources);
|
||||
RestoreShaderResources<DxbcProgramType::PixelShader> (m_state.ps.shaderResources);
|
||||
RestoreShaderResources<DxbcProgramType::ComputeShader> (m_state.cs.shaderResources);
|
||||
|
||||
RestoreUnorderedAccessViews<DxbcProgramType::PixelShader> (m_state.ps.unorderedAccessViews);
|
||||
RestoreUnorderedAccessViews<DxbcProgramType::ComputeShader> (m_state.cs.unorderedAccessViews);
|
||||
}
|
||||
|
||||
|
||||
template<DxbcProgramType Stage>
|
||||
void D3D11DeviceContext::RestoreConstantBuffers(
|
||||
D3D11ConstantBufferBindings& Bindings) {
|
||||
uint32_t slotId = computeConstantBufferBinding(Stage, 0);
|
||||
|
||||
for (uint32_t i = 0; i < Bindings.size(); i++) {
|
||||
BindConstantBuffer(slotId + i, Bindings[i].buffer.ptr(),
|
||||
Bindings[i].constantOffset, Bindings[i].constantBound);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
template<DxbcProgramType Stage>
|
||||
void D3D11DeviceContext::RestoreSamplers(
|
||||
D3D11SamplerBindings& Bindings) {
|
||||
uint32_t slotId = computeSamplerBinding(Stage, 0);
|
||||
|
||||
for (uint32_t i = 0; i < Bindings.size(); i++)
|
||||
BindSampler(slotId + i, Bindings[i]);
|
||||
}
|
||||
|
||||
|
||||
template<DxbcProgramType Stage>
|
||||
void D3D11DeviceContext::RestoreShaderResources(
|
||||
D3D11ShaderResourceBindings& Bindings) {
|
||||
uint32_t slotId = computeSrvBinding(Stage, 0);
|
||||
|
||||
for (uint32_t i = 0; i < Bindings.views.size(); i++)
|
||||
BindShaderResource(slotId + i, Bindings.views[i].ptr());
|
||||
}
|
||||
|
||||
|
||||
template<DxbcProgramType Stage>
|
||||
void D3D11DeviceContext::RestoreUnorderedAccessViews(
|
||||
D3D11UnorderedAccessBindings& Bindings) {
|
||||
uint32_t uavSlotId = computeUavBinding (Stage, 0);
|
||||
uint32_t ctrSlotId = computeUavCounterBinding(Stage, 0);
|
||||
|
||||
for (uint32_t i = 0; i < Bindings.size(); i++) {
|
||||
BindUnorderedAccessView(
|
||||
uavSlotId + i,
|
||||
Bindings[i].ptr(),
|
||||
ctrSlotId + i, ~0u);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
bool D3D11DeviceContext::TestRtvUavHazards(
|
||||
UINT NumRTVs,
|
||||
ID3D11RenderTargetView* const* ppRTVs,
|
||||
UINT NumUAVs,
|
||||
ID3D11UnorderedAccessView* const* ppUAVs) {
|
||||
if (NumRTVs == D3D11_KEEP_RENDER_TARGETS_AND_DEPTH_STENCIL) NumRTVs = 0;
|
||||
if (NumUAVs == D3D11_KEEP_UNORDERED_ACCESS_VIEWS) NumUAVs = 0;
|
||||
|
||||
for (uint32_t i = 0; i < NumRTVs; i++) {
|
||||
auto rtv = static_cast<D3D11RenderTargetView*>(ppRTVs[i]);
|
||||
|
||||
if (!rtv)
|
||||
continue;
|
||||
|
||||
for (uint32_t j = 0; j < i; j++) {
|
||||
if (CheckViewOverlap(rtv, static_cast<D3D11RenderTargetView*>(ppRTVs[j])))
|
||||
return true;
|
||||
}
|
||||
|
||||
if (rtv->HasBindFlag(D3D11_BIND_UNORDERED_ACCESS)) {
|
||||
for (uint32_t j = 0; j < NumUAVs; j++) {
|
||||
if (CheckViewOverlap(rtv, static_cast<D3D11UnorderedAccessView*>(ppUAVs[j])))
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for (uint32_t i = 0; i < NumUAVs; i++) {
|
||||
auto uav = static_cast<D3D11UnorderedAccessView*>(ppUAVs[i]);
|
||||
|
||||
if (!uav)
|
||||
continue;
|
||||
|
||||
for (uint32_t j = 0; j < i; j++) {
|
||||
if (CheckViewOverlap(uav, static_cast<D3D11UnorderedAccessView*>(ppUAVs[j])))
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
template<DxbcProgramType ShaderStage>
|
||||
bool D3D11DeviceContext::TestSrvHazards(
|
||||
D3D11ShaderResourceView* pView) {
|
||||
bool hazard = false;
|
||||
|
||||
if (ShaderStage == DxbcProgramType::ComputeShader) {
|
||||
int32_t uav = m_state.cs.uavMask.findNext(0);
|
||||
|
||||
while (uav >= 0 && !hazard) {
|
||||
hazard = CheckViewOverlap(pView, m_state.cs.unorderedAccessViews[uav].ptr());
|
||||
uav = m_state.cs.uavMask.findNext(uav + 1);
|
||||
}
|
||||
} else {
|
||||
hazard = CheckViewOverlap(pView, m_state.om.depthStencilView.ptr());
|
||||
|
||||
for (uint32_t i = 0; !hazard && i < m_state.om.maxRtv; i++)
|
||||
hazard = CheckViewOverlap(pView, m_state.om.renderTargetViews[i].ptr());
|
||||
|
||||
for (uint32_t i = 0; !hazard && i < m_state.om.maxUav; i++)
|
||||
hazard = CheckViewOverlap(pView, m_state.ps.unorderedAccessViews[i].ptr());
|
||||
}
|
||||
|
||||
return hazard;
|
||||
}
|
||||
|
||||
|
||||
template<DxbcProgramType ShaderStage, typename T>
|
||||
void D3D11DeviceContext::ResolveSrvHazards(
|
||||
T* pView,
|
||||
D3D11ShaderResourceBindings& Bindings) {
|
||||
uint32_t slotId = computeSrvBinding(ShaderStage, 0);
|
||||
int32_t srvId = Bindings.hazardous.findNext(0);
|
||||
|
||||
while (srvId >= 0) {
|
||||
auto srv = Bindings.views[srvId].ptr();
|
||||
|
||||
if (likely(srv && srv->TestHazards())) {
|
||||
bool hazard = CheckViewOverlap(pView, srv);
|
||||
|
||||
if (unlikely(hazard)) {
|
||||
Bindings.views[srvId] = nullptr;
|
||||
Bindings.hazardous.clr(srvId);
|
||||
|
||||
BindShaderResource(slotId + srvId, nullptr);
|
||||
}
|
||||
} else {
|
||||
// Avoid further redundant iterations
|
||||
Bindings.hazardous.clr(srvId);
|
||||
}
|
||||
|
||||
srvId = Bindings.hazardous.findNext(srvId + 1);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
template<typename T>
|
||||
void D3D11DeviceContext::ResolveCsSrvHazards(
|
||||
T* pView) {
|
||||
if (!pView) return;
|
||||
ResolveSrvHazards<DxbcProgramType::ComputeShader> (pView, m_state.cs.shaderResources);
|
||||
}
|
||||
|
||||
|
||||
template<typename T>
|
||||
void D3D11DeviceContext::ResolveOmSrvHazards(
|
||||
T* pView) {
|
||||
if (!pView) return;
|
||||
ResolveSrvHazards<DxbcProgramType::VertexShader> (pView, m_state.vs.shaderResources);
|
||||
ResolveSrvHazards<DxbcProgramType::HullShader> (pView, m_state.hs.shaderResources);
|
||||
ResolveSrvHazards<DxbcProgramType::DomainShader> (pView, m_state.ds.shaderResources);
|
||||
ResolveSrvHazards<DxbcProgramType::GeometryShader> (pView, m_state.gs.shaderResources);
|
||||
ResolveSrvHazards<DxbcProgramType::PixelShader> (pView, m_state.ps.shaderResources);
|
||||
}
|
||||
|
||||
|
||||
bool D3D11DeviceContext::ResolveOmRtvHazards(
|
||||
D3D11UnorderedAccessView* pView) {
|
||||
if (!pView || !pView->HasBindFlag(D3D11_BIND_RENDER_TARGET))
|
||||
return false;
|
||||
|
||||
bool hazard = false;
|
||||
|
||||
if (CheckViewOverlap(pView, m_state.om.depthStencilView.ptr())) {
|
||||
m_state.om.depthStencilView = nullptr;
|
||||
hazard = true;
|
||||
}
|
||||
|
||||
for (uint32_t i = 0; i < m_state.om.maxRtv; i++) {
|
||||
if (CheckViewOverlap(pView, m_state.om.renderTargetViews[i].ptr())) {
|
||||
m_state.om.renderTargetViews[i] = nullptr;
|
||||
hazard = true;
|
||||
}
|
||||
}
|
||||
|
||||
return hazard;
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::ResolveOmUavHazards(
|
||||
D3D11RenderTargetView* pView) {
|
||||
if (!pView || !pView->HasBindFlag(D3D11_BIND_UNORDERED_ACCESS))
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::UpdateResource(
|
||||
ID3D11Resource* pDstResource,
|
||||
UINT DstSubresource,
|
||||
const D3D11_BOX* pDstBox,
|
||||
const void* pSrcData,
|
||||
UINT SrcRowPitch,
|
||||
UINT SrcDepthPitch,
|
||||
UINT CopyFlags) {
|
||||
auto context = static_cast<ContextType*>(this);
|
||||
D3D10DeviceLock lock = context->LockContext();
|
||||
|
||||
if (!pDstResource)
|
||||
return;
|
||||
|
||||
uint32_t uavSlotId = computeUavBinding (DxbcProgramType::PixelShader, 0);
|
||||
uint32_t ctrSlotId = computeUavCounterBinding(DxbcProgramType::PixelShader, 0);
|
||||
// We need a different code path for buffers
|
||||
D3D11_RESOURCE_DIMENSION resourceType;
|
||||
pDstResource->GetType(&resourceType);
|
||||
|
||||
for (uint32_t i = 0; i < m_state.om.maxUav; i++) {
|
||||
if (CheckViewOverlap(pView, m_state.ps.unorderedAccessViews[i].ptr())) {
|
||||
m_state.ps.unorderedAccessViews[i] = nullptr;
|
||||
if (likely(resourceType == D3D11_RESOURCE_DIMENSION_BUFFER)) {
|
||||
const auto bufferResource = static_cast<D3D11Buffer*>(pDstResource);
|
||||
uint64_t bufferSize = bufferResource->Desc()->ByteWidth;
|
||||
|
||||
BindUnorderedAccessView(
|
||||
uavSlotId + i, nullptr,
|
||||
ctrSlotId + i, ~0u);
|
||||
// Provide a fast path for mapped buffer updates since some
|
||||
// games use UpdateSubresource to update constant buffers.
|
||||
if (likely(bufferResource->GetMapMode() == D3D11_COMMON_BUFFER_MAP_MODE_DIRECT) && likely(!pDstBox)) {
|
||||
context->UpdateMappedBuffer(bufferResource, 0, bufferSize, pSrcData, 0);
|
||||
return;
|
||||
}
|
||||
|
||||
// Validate buffer range to update
|
||||
uint64_t offset = 0;
|
||||
uint64_t length = bufferSize;
|
||||
|
||||
if (pDstBox) {
|
||||
offset = pDstBox->left;
|
||||
length = pDstBox->right - offset;
|
||||
}
|
||||
|
||||
if (unlikely(offset + length > bufferSize))
|
||||
return;
|
||||
|
||||
// Still try to be fast if a box is provided but we update the full buffer
|
||||
if (likely(bufferResource->GetMapMode() == D3D11_COMMON_BUFFER_MAP_MODE_DIRECT)) {
|
||||
CopyFlags &= D3D11_COPY_DISCARD | D3D11_COPY_NO_OVERWRITE;
|
||||
|
||||
if (likely(length == bufferSize) || unlikely(CopyFlags != 0)) {
|
||||
context->UpdateMappedBuffer(bufferResource, offset, length, pSrcData, CopyFlags);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
// Otherwise we can't really do anything fancy, so just do a GPU copy
|
||||
context->UpdateBuffer(bufferResource, offset, length, pSrcData);
|
||||
} else {
|
||||
D3D11CommonTexture* textureResource = GetCommonTexture(pDstResource);
|
||||
|
||||
context->UpdateTexture(textureResource,
|
||||
DstSubresource, pDstBox, pSrcData, SrcRowPitch, SrcDepthPitch);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
bool D3D11DeviceContext::ValidateRenderTargets(
|
||||
template<typename ContextType>
|
||||
bool D3D11CommonContext<ContextType>::ValidateRenderTargets(
|
||||
UINT NumViews,
|
||||
ID3D11RenderTargetView* const* ppRenderTargetViews,
|
||||
ID3D11DepthStencilView* pDepthStencilView) {
|
||||
Rc<DxvkImageView> refView;
|
||||
|
||||
|
||||
VkExtent3D dsvExtent = { 0u, 0u, 0u };
|
||||
VkExtent3D rtvExtent = { 0u, 0u, 0u };
|
||||
|
||||
if (pDepthStencilView != nullptr) {
|
||||
refView = static_cast<D3D11DepthStencilView*>(
|
||||
pDepthStencilView)->GetImageView();
|
||||
dsvExtent = refView->mipLevelExtent(0);
|
||||
}
|
||||
|
||||
|
||||
for (uint32_t i = 0; i < NumViews; i++) {
|
||||
if (ppRenderTargetViews[i] != nullptr) {
|
||||
auto curView = static_cast<D3D11RenderTargetView*>(
|
||||
ppRenderTargetViews[i])->GetImageView();
|
||||
|
||||
|
||||
if (!rtvExtent.width)
|
||||
rtvExtent = curView->mipLevelExtent(0);
|
||||
|
||||
if (refView != nullptr) {
|
||||
// Render target views must all have the same
|
||||
// size, sample count, layer count, and type
|
||||
// Render target views must all have the same sample count,
|
||||
// layer count, and type. The size can mismatch under certain
|
||||
// conditions, the D3D11 documentation is wrong here.
|
||||
if (curView->info().type != refView->info().type
|
||||
|| curView->info().numLayers != refView->info().numLayers)
|
||||
return false;
|
||||
|
||||
|
||||
if (curView->imageInfo().sampleCount
|
||||
!= refView->imageInfo().sampleCount)
|
||||
return false;
|
||||
|
||||
// Color targets must all be the same size
|
||||
VkExtent3D curExtent = curView->mipLevelExtent(0);
|
||||
|
||||
if (curExtent.width != rtvExtent.width
|
||||
|| curExtent.height != rtvExtent.height)
|
||||
return false;
|
||||
} else {
|
||||
// Set reference view. All remaining views
|
||||
// must be compatible to the reference view.
|
||||
@ -4441,73 +5375,21 @@ namespace dxvk {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Based on testing, the depth-stencil target is allowed
|
||||
// to be larger than all color targets, but not smaller
|
||||
if (rtvExtent.width && dsvExtent.width) {
|
||||
if (rtvExtent.width > dsvExtent.width
|
||||
|| rtvExtent.height > dsvExtent.height)
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
VkClearValue D3D11DeviceContext::ConvertColorValue(
|
||||
const FLOAT Color[4],
|
||||
const DxvkFormatInfo* pFormatInfo) {
|
||||
VkClearValue result;
|
||||
|
||||
if (pFormatInfo->aspectMask & VK_IMAGE_ASPECT_COLOR_BIT) {
|
||||
for (uint32_t i = 0; i < 4; i++) {
|
||||
if (pFormatInfo->flags.test(DxvkFormatFlag::SampledUInt))
|
||||
result.color.uint32[i] = uint32_t(std::max(0.0f, Color[i]));
|
||||
else if (pFormatInfo->flags.test(DxvkFormatFlag::SampledSInt))
|
||||
result.color.int32[i] = int32_t(Color[i]);
|
||||
else
|
||||
result.color.float32[i] = Color[i];
|
||||
}
|
||||
} else {
|
||||
result.depthStencil.depth = Color[0];
|
||||
result.depthStencil.stencil = 0;
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
DxvkDataSlice D3D11DeviceContext::AllocUpdateBufferSlice(size_t Size) {
|
||||
constexpr size_t UpdateBufferSize = 1 * 1024 * 1024;
|
||||
|
||||
if (Size >= UpdateBufferSize) {
|
||||
Rc<DxvkDataBuffer> buffer = new DxvkDataBuffer(Size);
|
||||
return buffer->alloc(Size);
|
||||
} else {
|
||||
if (m_updateBuffer == nullptr)
|
||||
m_updateBuffer = new DxvkDataBuffer(UpdateBufferSize);
|
||||
|
||||
DxvkDataSlice slice = m_updateBuffer->alloc(Size);
|
||||
|
||||
if (slice.ptr() == nullptr) {
|
||||
m_updateBuffer = new DxvkDataBuffer(UpdateBufferSize);
|
||||
slice = m_updateBuffer->alloc(Size);
|
||||
}
|
||||
|
||||
return slice;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
DxvkBufferSlice D3D11DeviceContext::AllocStagingBuffer(
|
||||
VkDeviceSize Size) {
|
||||
return m_staging.alloc(256, Size);
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::ResetStagingBuffer() {
|
||||
m_staging.reset();
|
||||
}
|
||||
|
||||
|
||||
DxvkCsChunkRef D3D11DeviceContext::AllocCsChunk() {
|
||||
return m_parent->AllocCsChunk(m_csFlags);
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::InitDefaultPrimitiveTopology(
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::InitDefaultPrimitiveTopology(
|
||||
DxvkInputAssemblyState* pIaState) {
|
||||
pIaState->primitiveTopology = VK_PRIMITIVE_TOPOLOGY_MAX_ENUM;
|
||||
pIaState->primitiveRestart = VK_FALSE;
|
||||
@ -4515,7 +5397,8 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::InitDefaultRasterizerState(
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::InitDefaultRasterizerState(
|
||||
DxvkRasterizerState* pRsState) {
|
||||
pRsState->polygonMode = VK_POLYGON_MODE_FILL;
|
||||
pRsState->cullMode = VK_CULL_MODE_BACK_BIT;
|
||||
@ -4524,10 +5407,13 @@ namespace dxvk {
|
||||
pRsState->depthBiasEnable = VK_FALSE;
|
||||
pRsState->conservativeMode = VK_CONSERVATIVE_RASTERIZATION_MODE_DISABLED_EXT;
|
||||
pRsState->sampleCount = 0;
|
||||
pRsState->flatShading = VK_FALSE;
|
||||
pRsState->lineMode = VK_LINE_RASTERIZATION_MODE_DEFAULT_EXT;
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::InitDefaultDepthStencilState(
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::InitDefaultDepthStencilState(
|
||||
DxvkDepthStencilState* pDsState) {
|
||||
VkStencilOpState stencilOp;
|
||||
stencilOp.failOp = VK_STENCIL_OP_KEEP;
|
||||
@ -4546,8 +5432,9 @@ namespace dxvk {
|
||||
pDsState->stencilOpBack = stencilOp;
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::InitDefaultBlendState(
|
||||
|
||||
template<typename ContextType>
|
||||
void D3D11CommonContext<ContextType>::InitDefaultBlendState(
|
||||
DxvkBlendMode* pCbState,
|
||||
DxvkLogicOpState* pLoState,
|
||||
DxvkMultisampleState* pMsState,
|
||||
@ -4569,25 +5456,8 @@ namespace dxvk {
|
||||
pMsState->enableAlphaToCoverage = VK_FALSE;
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeviceContext::TrackResourceSequenceNumber(
|
||||
ID3D11Resource* pResource) {
|
||||
if (!pResource)
|
||||
return;
|
||||
|
||||
D3D11CommonTexture* texture = GetCommonTexture(pResource);
|
||||
|
||||
if (texture) {
|
||||
if (texture->HasSequenceNumber()) {
|
||||
for (uint32_t i = 0; i < texture->CountSubresources(); i++)
|
||||
TrackTextureSequenceNumber(texture, i);
|
||||
}
|
||||
} else {
|
||||
D3D11Buffer* buffer = static_cast<D3D11Buffer*>(pResource);
|
||||
|
||||
if (buffer->HasSequenceNumber())
|
||||
TrackBufferSequenceNumber(buffer);
|
||||
}
|
||||
}
|
||||
// Explicitly instantiate here
|
||||
template class D3D11CommonContext<D3D11DeferredContext>;
|
||||
template class D3D11CommonContext<D3D11ImmediateContext>;
|
||||
|
||||
}
|
||||
|
@ -1,5 +1,8 @@
|
||||
#pragma once
|
||||
|
||||
#include <type_traits>
|
||||
#include <vector>
|
||||
|
||||
#include "../dxvk/dxvk_adapter.h"
|
||||
#include "../dxvk/dxvk_cs.h"
|
||||
#include "../dxvk/dxvk_device.h"
|
||||
@ -7,7 +10,10 @@
|
||||
|
||||
#include "../d3d10/d3d10_multithread.h"
|
||||
|
||||
#include "../util/util_flush.h"
|
||||
|
||||
#include "d3d11_annotation.h"
|
||||
#include "d3d11_buffer.h"
|
||||
#include "d3d11_cmd.h"
|
||||
#include "d3d11_context_ext.h"
|
||||
#include "d3d11_context_state.h"
|
||||
@ -15,27 +21,78 @@
|
||||
#include "d3d11_texture.h"
|
||||
|
||||
namespace dxvk {
|
||||
|
||||
class D3D11Device;
|
||||
|
||||
class D3D11DeviceContext : public D3D11DeviceChild<ID3D11DeviceContext4> {
|
||||
friend class D3D11DeviceContextExt;
|
||||
// Needed in order to call EmitCs for pushing markers
|
||||
friend class D3D11UserDefinedAnnotation;
|
||||
|
||||
class D3D11DeferredContext;
|
||||
class D3D11ImmediateContext;
|
||||
|
||||
template<bool IsDeferred>
|
||||
struct D3D11ContextObjectForwarder;
|
||||
|
||||
/**
|
||||
* \brief Object forwarder for immediate contexts
|
||||
*
|
||||
* Binding methods can use this to efficiently bind objects
|
||||
* to the DXVK context without redundant reference counting.
|
||||
*/
|
||||
template<>
|
||||
struct D3D11ContextObjectForwarder<false> {
|
||||
template<typename T>
|
||||
static T&& move(T& object) {
|
||||
return std::move(object);
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* \brief Object forwarder for deferred contexts
|
||||
*
|
||||
* This forwarder will create a copy of the object passed
|
||||
* into it, so that CS chunks can be reused if necessary.
|
||||
*/
|
||||
template<>
|
||||
struct D3D11ContextObjectForwarder<true> {
|
||||
template<typename T>
|
||||
static T move(const T& object) {
|
||||
return object;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* \brief Common D3D11 device context implementation
|
||||
*
|
||||
* Implements all common device context methods, but since this is
|
||||
* templates with the actual context type (deferred or immediate),
|
||||
* all methods can call back into context-specific methods without
|
||||
* having to use virtual methods.
|
||||
*/
|
||||
template<typename ContextType>
|
||||
class D3D11CommonContext : public D3D11DeviceChild<ID3D11DeviceContext4> {
|
||||
constexpr static bool IsDeferred = std::is_same_v<ContextType, D3D11DeferredContext>;
|
||||
using Forwarder = D3D11ContextObjectForwarder<IsDeferred>;
|
||||
|
||||
template<typename T> friend class D3D11DeviceContextExt;
|
||||
template<typename T> friend class D3D11UserDefinedAnnotation;
|
||||
|
||||
constexpr static VkDeviceSize StagingBufferSize = 4ull << 20;
|
||||
public:
|
||||
|
||||
D3D11DeviceContext(
|
||||
D3D11CommonContext(
|
||||
D3D11Device* pParent,
|
||||
const Rc<DxvkDevice>& Device,
|
||||
UINT ContextFlags,
|
||||
DxvkCsChunkFlags CsFlags);
|
||||
~D3D11DeviceContext();
|
||||
|
||||
|
||||
~D3D11CommonContext();
|
||||
|
||||
HRESULT STDMETHODCALLTYPE QueryInterface(
|
||||
REFIID riid,
|
||||
void** ppvObject);
|
||||
|
||||
D3D11_DEVICE_CONTEXT_TYPE STDMETHODCALLTYPE GetType();
|
||||
|
||||
UINT STDMETHODCALLTYPE GetContextFlags();
|
||||
|
||||
void STDMETHODCALLTYPE ClearState();
|
||||
|
||||
void STDMETHODCALLTYPE DiscardResource(ID3D11Resource *pResource);
|
||||
|
||||
void STDMETHODCALLTYPE DiscardView(ID3D11View* pResourceView);
|
||||
@ -44,17 +101,7 @@ namespace dxvk {
|
||||
ID3D11View* pResourceView,
|
||||
const D3D11_RECT* pRects,
|
||||
UINT NumRects);
|
||||
|
||||
void STDMETHODCALLTYPE ClearState();
|
||||
|
||||
void STDMETHODCALLTYPE SetPredication(
|
||||
ID3D11Predicate* pPredicate,
|
||||
BOOL PredicateValue);
|
||||
|
||||
void STDMETHODCALLTYPE GetPredication(
|
||||
ID3D11Predicate** ppPredicate,
|
||||
BOOL* pPredicateValue);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE CopySubresourceRegion(
|
||||
ID3D11Resource* pDstResource,
|
||||
UINT DstSubresource,
|
||||
@ -64,7 +111,7 @@ namespace dxvk {
|
||||
ID3D11Resource* pSrcResource,
|
||||
UINT SrcSubresource,
|
||||
const D3D11_BOX* pSrcBox);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE CopySubresourceRegion1(
|
||||
ID3D11Resource* pDstResource,
|
||||
UINT DstSubresource,
|
||||
@ -75,58 +122,34 @@ namespace dxvk {
|
||||
UINT SrcSubresource,
|
||||
const D3D11_BOX* pSrcBox,
|
||||
UINT CopyFlags);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE CopyResource(
|
||||
ID3D11Resource* pDstResource,
|
||||
ID3D11Resource* pSrcResource);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE CopyStructureCount(
|
||||
ID3D11Buffer* pDstBuffer,
|
||||
UINT DstAlignedByteOffset,
|
||||
ID3D11UnorderedAccessView* pSrcView);
|
||||
|
||||
void STDMETHODCALLTYPE CopyTiles(
|
||||
ID3D11Resource* pTiledResource,
|
||||
const D3D11_TILED_RESOURCE_COORDINATE* pTileRegionStartCoordinate,
|
||||
const D3D11_TILE_REGION_SIZE* pTileRegionSize,
|
||||
ID3D11Buffer* pBuffer,
|
||||
UINT64 BufferStartOffsetInBytes,
|
||||
UINT Flags);
|
||||
|
||||
HRESULT STDMETHODCALLTYPE CopyTileMappings(
|
||||
ID3D11Resource* pDestTiledResource,
|
||||
const D3D11_TILED_RESOURCE_COORDINATE* pDestRegionStartCoordinate,
|
||||
ID3D11Resource* pSourceTiledResource,
|
||||
const D3D11_TILED_RESOURCE_COORDINATE* pSourceRegionStartCoordinate,
|
||||
const D3D11_TILE_REGION_SIZE* pTileRegionSize,
|
||||
UINT Flags);
|
||||
|
||||
HRESULT STDMETHODCALLTYPE ResizeTilePool(
|
||||
ID3D11Buffer* pTilePool,
|
||||
UINT64 NewSizeInBytes);
|
||||
|
||||
void STDMETHODCALLTYPE TiledResourceBarrier(
|
||||
ID3D11DeviceChild* pTiledResourceOrViewAccessBeforeBarrier,
|
||||
ID3D11DeviceChild* pTiledResourceOrViewAccessAfterBarrier);
|
||||
|
||||
void STDMETHODCALLTYPE ClearRenderTargetView(
|
||||
ID3D11RenderTargetView* pRenderTargetView,
|
||||
const FLOAT ColorRGBA[4]);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE ClearUnorderedAccessViewUint(
|
||||
ID3D11UnorderedAccessView* pUnorderedAccessView,
|
||||
const UINT Values[4]);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE ClearUnorderedAccessViewFloat(
|
||||
ID3D11UnorderedAccessView* pUnorderedAccessView,
|
||||
const FLOAT Values[4]);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE ClearDepthStencilView(
|
||||
ID3D11DepthStencilView* pDepthStencilView,
|
||||
UINT ClearFlags,
|
||||
FLOAT Depth,
|
||||
UINT8 Stencil);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE ClearView(
|
||||
ID3D11View *pView,
|
||||
const FLOAT Color[4],
|
||||
@ -135,122 +158,113 @@ namespace dxvk {
|
||||
|
||||
void STDMETHODCALLTYPE GenerateMips(
|
||||
ID3D11ShaderResourceView* pShaderResourceView);
|
||||
|
||||
HRESULT STDMETHODCALLTYPE UpdateTileMappings(
|
||||
ID3D11Resource* pTiledResource,
|
||||
UINT NumTiledResourceRegions,
|
||||
const D3D11_TILED_RESOURCE_COORDINATE* pTiledResourceRegionStartCoordinates,
|
||||
const D3D11_TILE_REGION_SIZE* pTiledResourceRegionSizes,
|
||||
ID3D11Buffer* pTilePool,
|
||||
UINT NumRanges,
|
||||
const UINT* pRangeFlags,
|
||||
const UINT* pTilePoolStartOffsets,
|
||||
const UINT* pRangeTileCounts,
|
||||
UINT Flags);
|
||||
|
||||
void STDMETHODCALLTYPE UpdateTiles(
|
||||
ID3D11Resource* pDestTiledResource,
|
||||
const D3D11_TILED_RESOURCE_COORDINATE* pDestTileRegionStartCoordinate,
|
||||
const D3D11_TILE_REGION_SIZE* pDestTileRegionSize,
|
||||
const void* pSourceTileData,
|
||||
UINT Flags);
|
||||
|
||||
void STDMETHODCALLTYPE SetResourceMinLOD(
|
||||
ID3D11Resource* pResource,
|
||||
FLOAT MinLOD);
|
||||
|
||||
FLOAT STDMETHODCALLTYPE GetResourceMinLOD(
|
||||
ID3D11Resource* pResource);
|
||||
|
||||
void STDMETHODCALLTYPE ResolveSubresource(
|
||||
ID3D11Resource* pDstResource,
|
||||
UINT DstSubresource,
|
||||
ID3D11Resource* pSrcResource,
|
||||
UINT SrcSubresource,
|
||||
DXGI_FORMAT Format);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE UpdateSubresource(
|
||||
ID3D11Resource* pDstResource,
|
||||
UINT DstSubresource,
|
||||
const D3D11_BOX* pDstBox,
|
||||
const void* pSrcData,
|
||||
UINT SrcRowPitch,
|
||||
UINT SrcDepthPitch);
|
||||
|
||||
void STDMETHODCALLTYPE UpdateSubresource1(
|
||||
ID3D11Resource* pDstResource,
|
||||
UINT DstSubresource,
|
||||
const D3D11_BOX* pDstBox,
|
||||
const void* pSrcData,
|
||||
UINT SrcRowPitch,
|
||||
UINT SrcDepthPitch,
|
||||
UINT CopyFlags);
|
||||
|
||||
void STDMETHODCALLTYPE DrawAuto();
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE Draw(
|
||||
UINT VertexCount,
|
||||
UINT StartVertexLocation);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE DrawIndexed(
|
||||
UINT IndexCount,
|
||||
UINT StartIndexLocation,
|
||||
INT BaseVertexLocation);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE DrawInstanced(
|
||||
UINT VertexCountPerInstance,
|
||||
UINT InstanceCount,
|
||||
UINT StartVertexLocation,
|
||||
UINT StartInstanceLocation);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE DrawIndexedInstanced(
|
||||
UINT IndexCountPerInstance,
|
||||
UINT InstanceCount,
|
||||
UINT StartIndexLocation,
|
||||
INT BaseVertexLocation,
|
||||
UINT StartInstanceLocation);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE DrawIndexedInstancedIndirect(
|
||||
ID3D11Buffer* pBufferForArgs,
|
||||
UINT AlignedByteOffsetForArgs);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE DrawInstancedIndirect(
|
||||
ID3D11Buffer* pBufferForArgs,
|
||||
UINT AlignedByteOffsetForArgs);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE Dispatch(
|
||||
UINT ThreadGroupCountX,
|
||||
UINT ThreadGroupCountY,
|
||||
UINT ThreadGroupCountZ);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE DispatchIndirect(
|
||||
ID3D11Buffer* pBufferForArgs,
|
||||
UINT AlignedByteOffsetForArgs);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE IASetInputLayout(
|
||||
ID3D11InputLayout* pInputLayout);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE IASetPrimitiveTopology(
|
||||
D3D11_PRIMITIVE_TOPOLOGY Topology);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE IASetVertexBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppVertexBuffers,
|
||||
const UINT* pStrides,
|
||||
const UINT* pOffsets);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE IASetIndexBuffer(
|
||||
ID3D11Buffer* pIndexBuffer,
|
||||
DXGI_FORMAT Format,
|
||||
UINT Offset);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE IAGetInputLayout(
|
||||
ID3D11InputLayout** ppInputLayout);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE IAGetPrimitiveTopology(
|
||||
D3D11_PRIMITIVE_TOPOLOGY* pTopology);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE IAGetVertexBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppVertexBuffers,
|
||||
UINT* pStrides,
|
||||
UINT* pOffsets);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE IAGetIndexBuffer(
|
||||
ID3D11Buffer** ppIndexBuffer,
|
||||
DXGI_FORMAT* pFormat,
|
||||
UINT* pOffset);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE VSSetShader(
|
||||
ID3D11VertexShader* pVertexShader,
|
||||
ID3D11ClassInstance* const* ppClassInstances,
|
||||
UINT NumClassInstances);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE VSSetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
@ -262,22 +276,22 @@ namespace dxvk {
|
||||
ID3D11Buffer* const* ppConstantBuffers,
|
||||
const UINT* pFirstConstant,
|
||||
const UINT* pNumConstants);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE VSSetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView* const* ppShaderResourceViews);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE VSSetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState* const* ppSamplers);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE VSGetShader(
|
||||
ID3D11VertexShader** ppVertexShader,
|
||||
ID3D11ClassInstance** ppClassInstances,
|
||||
UINT* pNumClassInstances);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE VSGetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
@ -289,49 +303,49 @@ namespace dxvk {
|
||||
ID3D11Buffer** ppConstantBuffers,
|
||||
UINT* pFirstConstant,
|
||||
UINT* pNumConstants);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE VSGetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView** ppShaderResourceViews);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE VSGetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState** ppSamplers);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE HSSetShader(
|
||||
ID3D11HullShader* pHullShader,
|
||||
ID3D11ClassInstance* const* ppClassInstances,
|
||||
UINT NumClassInstances);
|
||||
|
||||
void STDMETHODCALLTYPE HSSetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView* const* ppShaderResourceViews);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE HSSetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE HSSetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers,
|
||||
const UINT* pFirstConstant,
|
||||
const UINT* pNumConstants);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE HSSetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView* const* ppShaderResourceViews);
|
||||
|
||||
void STDMETHODCALLTYPE HSSetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState* const* ppSamplers);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE HSGetShader(
|
||||
ID3D11HullShader** ppHullShader,
|
||||
ID3D11ClassInstance** ppClassInstances,
|
||||
UINT* pNumClassInstances);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE HSGetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
@ -343,27 +357,22 @@ namespace dxvk {
|
||||
ID3D11Buffer** ppConstantBuffers,
|
||||
UINT* pFirstConstant,
|
||||
UINT* pNumConstants);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE HSGetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView** ppShaderResourceViews);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE HSGetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState** ppSamplers);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE DSSetShader(
|
||||
ID3D11DomainShader* pDomainShader,
|
||||
ID3D11ClassInstance* const* ppClassInstances,
|
||||
UINT NumClassInstances);
|
||||
|
||||
void STDMETHODCALLTYPE DSSetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView* const* ppShaderResourceViews);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE DSSetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
@ -375,49 +384,54 @@ namespace dxvk {
|
||||
ID3D11Buffer* const* ppConstantBuffers,
|
||||
const UINT* pFirstConstant,
|
||||
const UINT* pNumConstants);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE DSSetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView* const* ppShaderResourceViews);
|
||||
|
||||
void STDMETHODCALLTYPE DSSetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState* const* ppSamplers);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE DSGetShader(
|
||||
ID3D11DomainShader** ppDomainShader,
|
||||
ID3D11ClassInstance** ppClassInstances,
|
||||
UINT* pNumClassInstances);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE DSGetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppConstantBuffers);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE DSGetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppConstantBuffers,
|
||||
UINT* pFirstConstant,
|
||||
UINT* pNumConstants);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE DSGetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView** ppShaderResourceViews);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE DSGetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState** ppSamplers);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE GSSetShader(
|
||||
ID3D11GeometryShader* pShader,
|
||||
ID3D11ClassInstance* const* ppClassInstances,
|
||||
UINT NumClassInstances);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE GSSetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE GSSetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
@ -429,44 +443,44 @@ namespace dxvk {
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView* const* ppShaderResourceViews);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE GSSetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState* const* ppSamplers);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE GSGetShader(
|
||||
ID3D11GeometryShader** ppGeometryShader,
|
||||
ID3D11ClassInstance** ppClassInstances,
|
||||
UINT* pNumClassInstances);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE GSGetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppConstantBuffers);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE GSGetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppConstantBuffers,
|
||||
UINT* pFirstConstant,
|
||||
UINT* pNumConstants);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE GSGetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView** ppShaderResourceViews);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE GSGetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState** ppSamplers);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE PSSetShader(
|
||||
ID3D11PixelShader* pPixelShader,
|
||||
ID3D11ClassInstance* const* ppClassInstances,
|
||||
UINT NumClassInstances);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE PSSetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
@ -478,27 +492,27 @@ namespace dxvk {
|
||||
ID3D11Buffer* const* ppConstantBuffers,
|
||||
const UINT* pFirstConstant,
|
||||
const UINT* pNumConstants);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE PSSetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView* const* ppShaderResourceViews);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE PSSetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState* const* ppSamplers);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE PSGetShader(
|
||||
ID3D11PixelShader** ppPixelShader,
|
||||
ID3D11ClassInstance** ppClassInstances,
|
||||
UINT* pNumClassInstances);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE PSGetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppConstantBuffers);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE PSGetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
@ -510,82 +524,82 @@ namespace dxvk {
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView** ppShaderResourceViews);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE PSGetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState** ppSamplers);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE CSSetShader(
|
||||
ID3D11ComputeShader* pComputeShader,
|
||||
ID3D11ClassInstance* const* ppClassInstances,
|
||||
UINT NumClassInstances);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE CSSetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE CSSetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers,
|
||||
const UINT* pFirstConstant,
|
||||
const UINT* pNumConstants);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE CSSetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView* const* ppShaderResourceViews);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE CSSetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState* const* ppSamplers);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE CSSetUnorderedAccessViews(
|
||||
UINT StartSlot,
|
||||
UINT NumUAVs,
|
||||
ID3D11UnorderedAccessView* const* ppUnorderedAccessViews,
|
||||
const UINT* pUAVInitialCounts);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE CSGetShader(
|
||||
ID3D11ComputeShader** ppComputeShader,
|
||||
ID3D11ClassInstance** ppClassInstances,
|
||||
UINT* pNumClassInstances);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE CSGetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppConstantBuffers);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE CSGetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppConstantBuffers,
|
||||
UINT* pFirstConstant,
|
||||
UINT* pNumConstants);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE CSGetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView** ppShaderResourceViews);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE CSGetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState** ppSamplers);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE CSGetUnorderedAccessViews(
|
||||
UINT StartSlot,
|
||||
UINT NumUAVs,
|
||||
ID3D11UnorderedAccessView** ppUnorderedAccessViews);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE OMSetRenderTargets(
|
||||
UINT NumViews,
|
||||
ID3D11RenderTargetView* const* ppRenderTargetViews,
|
||||
ID3D11DepthStencilView* pDepthStencilView);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE OMSetRenderTargetsAndUnorderedAccessViews(
|
||||
UINT NumRTVs,
|
||||
ID3D11RenderTargetView* const* ppRenderTargetViews,
|
||||
@ -594,21 +608,21 @@ namespace dxvk {
|
||||
UINT NumUAVs,
|
||||
ID3D11UnorderedAccessView* const* ppUnorderedAccessViews,
|
||||
const UINT* pUAVInitialCounts);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE OMSetBlendState(
|
||||
ID3D11BlendState* pBlendState,
|
||||
const FLOAT BlendFactor[4],
|
||||
UINT SampleMask);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE OMSetDepthStencilState(
|
||||
ID3D11DepthStencilState* pDepthStencilState,
|
||||
UINT StencilRef);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE OMGetRenderTargets(
|
||||
UINT NumViews,
|
||||
ID3D11RenderTargetView** ppRenderTargetViews,
|
||||
ID3D11DepthStencilView** ppDepthStencilView);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE OMGetRenderTargetsAndUnorderedAccessViews(
|
||||
UINT NumRTVs,
|
||||
ID3D11RenderTargetView** ppRenderTargetViews,
|
||||
@ -616,52 +630,110 @@ namespace dxvk {
|
||||
UINT UAVStartSlot,
|
||||
UINT NumUAVs,
|
||||
ID3D11UnorderedAccessView** ppUnorderedAccessViews);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE OMGetBlendState(
|
||||
ID3D11BlendState** ppBlendState,
|
||||
FLOAT BlendFactor[4],
|
||||
UINT* pSampleMask);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE OMGetDepthStencilState(
|
||||
ID3D11DepthStencilState** ppDepthStencilState,
|
||||
UINT* pStencilRef);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE RSSetState(
|
||||
ID3D11RasterizerState* pRasterizerState);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE RSSetViewports(
|
||||
UINT NumViewports,
|
||||
const D3D11_VIEWPORT* pViewports);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE RSSetScissorRects(
|
||||
UINT NumRects,
|
||||
const D3D11_RECT* pRects);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE RSGetState(
|
||||
ID3D11RasterizerState** ppRasterizerState);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE RSGetViewports(
|
||||
UINT* pNumViewports,
|
||||
D3D11_VIEWPORT* pViewports);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE RSGetScissorRects(
|
||||
UINT* pNumRects,
|
||||
D3D11_RECT* pRects);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE SOSetTargets(
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppSOTargets,
|
||||
const UINT* pOffsets);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE SOGetTargets(
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppSOTargets);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE SOGetTargetsWithOffsets(
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppSOTargets,
|
||||
UINT* pOffsets);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE SetPredication(
|
||||
ID3D11Predicate* pPredicate,
|
||||
BOOL PredicateValue);
|
||||
|
||||
void STDMETHODCALLTYPE GetPredication(
|
||||
ID3D11Predicate** ppPredicate,
|
||||
BOOL* pPredicateValue);
|
||||
|
||||
void STDMETHODCALLTYPE SetResourceMinLOD(
|
||||
ID3D11Resource* pResource,
|
||||
FLOAT MinLOD);
|
||||
|
||||
FLOAT STDMETHODCALLTYPE GetResourceMinLOD(
|
||||
ID3D11Resource* pResource);
|
||||
|
||||
void STDMETHODCALLTYPE CopyTiles(
|
||||
ID3D11Resource* pTiledResource,
|
||||
const D3D11_TILED_RESOURCE_COORDINATE* pTileRegionStartCoordinate,
|
||||
const D3D11_TILE_REGION_SIZE* pTileRegionSize,
|
||||
ID3D11Buffer* pBuffer,
|
||||
UINT64 BufferStartOffsetInBytes,
|
||||
UINT Flags);
|
||||
|
||||
HRESULT STDMETHODCALLTYPE CopyTileMappings(
|
||||
ID3D11Resource* pDestTiledResource,
|
||||
const D3D11_TILED_RESOURCE_COORDINATE* pDestRegionCoordinate,
|
||||
ID3D11Resource* pSourceTiledResource,
|
||||
const D3D11_TILED_RESOURCE_COORDINATE* pSourceRegionCoordinate,
|
||||
const D3D11_TILE_REGION_SIZE* pTileRegionSize,
|
||||
UINT Flags);
|
||||
|
||||
HRESULT STDMETHODCALLTYPE ResizeTilePool(
|
||||
ID3D11Buffer* pTilePool,
|
||||
UINT64 NewSizeInBytes);
|
||||
|
||||
void STDMETHODCALLTYPE TiledResourceBarrier(
|
||||
ID3D11DeviceChild* pTiledResourceOrViewAccessBeforeBarrier,
|
||||
ID3D11DeviceChild* pTiledResourceOrViewAccessAfterBarrier);
|
||||
|
||||
HRESULT STDMETHODCALLTYPE UpdateTileMappings(
|
||||
ID3D11Resource* pTiledResource,
|
||||
UINT NumRegions,
|
||||
const D3D11_TILED_RESOURCE_COORDINATE* pRegionCoordinates,
|
||||
const D3D11_TILE_REGION_SIZE* pRegionSizes,
|
||||
ID3D11Buffer* pTilePool,
|
||||
UINT NumRanges,
|
||||
const UINT* pRangeFlags,
|
||||
const UINT* pRangeTileOffsets,
|
||||
const UINT* pRangeTileCounts,
|
||||
UINT Flags);
|
||||
|
||||
void STDMETHODCALLTYPE UpdateTiles(
|
||||
ID3D11Resource* pDestTiledResource,
|
||||
const D3D11_TILED_RESOURCE_COORDINATE* pDestTileRegionStartCoordinate,
|
||||
const D3D11_TILE_REGION_SIZE* pDestTileRegionSize,
|
||||
const void* pSourceTileData,
|
||||
UINT Flags);
|
||||
|
||||
BOOL STDMETHODCALLTYPE IsAnnotationEnabled();
|
||||
|
||||
void STDMETHODCALLTYPE SetMarkerInt(
|
||||
@ -676,7 +748,7 @@ namespace dxvk {
|
||||
|
||||
void STDMETHODCALLTYPE GetHardwareProtectionState(
|
||||
BOOL* pHwProtectionEnable);
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE SetHardwareProtectionState(
|
||||
BOOL HwProtectionEnable);
|
||||
|
||||
@ -686,29 +758,30 @@ namespace dxvk {
|
||||
VkImageLayout OldLayout,
|
||||
VkImageLayout NewLayout);
|
||||
|
||||
D3D10DeviceLock LockContext() {
|
||||
return m_multithread.AcquireLock();
|
||||
}
|
||||
|
||||
protected:
|
||||
|
||||
D3D11DeviceContextExt m_contextExt;
|
||||
D3D10Multithread m_multithread;
|
||||
|
||||
|
||||
D3D11DeviceContextExt<ContextType> m_contextExt;
|
||||
D3D11UserDefinedAnnotation<ContextType> m_annotation;
|
||||
|
||||
Rc<DxvkDevice> m_device;
|
||||
Rc<DxvkDataBuffer> m_updateBuffer;
|
||||
|
||||
D3D11ContextState m_state;
|
||||
UINT m_flags;
|
||||
|
||||
DxvkStagingBuffer m_staging;
|
||||
|
||||
//has to be declared after m_device, as compiler initialize in order of declaration in the class
|
||||
D3D11UserDefinedAnnotation m_annotation;
|
||||
Rc<DxvkDataBuffer> m_updateBuffer;
|
||||
|
||||
DxvkCsChunkFlags m_csFlags;
|
||||
DxvkCsChunkRef m_csChunk;
|
||||
|
||||
D3D11ContextState m_state;
|
||||
D3D11CmdData* m_cmdData;
|
||||
|
||||
DxvkCsChunkRef AllocCsChunk();
|
||||
|
||||
DxvkDataSlice AllocUpdateBufferSlice(size_t Size);
|
||||
|
||||
DxvkBufferSlice AllocStagingBuffer(
|
||||
VkDeviceSize Size);
|
||||
|
||||
void ApplyInputLayout();
|
||||
|
||||
void ApplyPrimitiveTopology();
|
||||
@ -723,54 +796,81 @@ namespace dxvk {
|
||||
|
||||
void ApplyRasterizerState();
|
||||
|
||||
void ApplyRasterizerSampleCount();
|
||||
|
||||
void ApplyViewportState();
|
||||
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void BindShader(
|
||||
const D3D11CommonShader* pShaderModule);
|
||||
|
||||
|
||||
void BindFramebuffer();
|
||||
|
||||
|
||||
void BindDrawBuffers(
|
||||
D3D11Buffer* pBufferForArgs,
|
||||
D3D11Buffer* pBufferForCount);
|
||||
|
||||
|
||||
void BindVertexBuffer(
|
||||
UINT Slot,
|
||||
D3D11Buffer* pBuffer,
|
||||
UINT Offset,
|
||||
UINT Stride);
|
||||
|
||||
|
||||
void BindVertexBufferRange(
|
||||
UINT Slot,
|
||||
D3D11Buffer* pBuffer,
|
||||
UINT Offset,
|
||||
UINT Stride);
|
||||
|
||||
void BindIndexBuffer(
|
||||
D3D11Buffer* pBuffer,
|
||||
UINT Offset,
|
||||
DXGI_FORMAT Format);
|
||||
|
||||
|
||||
void BindIndexBufferRange(
|
||||
D3D11Buffer* pBuffer,
|
||||
UINT Offset,
|
||||
DXGI_FORMAT Format);
|
||||
|
||||
void BindXfbBuffer(
|
||||
UINT Slot,
|
||||
D3D11Buffer* pBuffer,
|
||||
UINT Offset);
|
||||
|
||||
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void BindConstantBuffer(
|
||||
UINT Slot,
|
||||
D3D11Buffer* pBuffer,
|
||||
UINT Offset,
|
||||
UINT Length);
|
||||
|
||||
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void BindConstantBufferRange(
|
||||
UINT Slot,
|
||||
UINT Offset,
|
||||
UINT Length);
|
||||
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void BindSampler(
|
||||
UINT Slot,
|
||||
D3D11SamplerState* pSampler);
|
||||
|
||||
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void BindShaderResource(
|
||||
UINT Slot,
|
||||
D3D11ShaderResourceView* pResource);
|
||||
|
||||
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void BindUnorderedAccessView(
|
||||
UINT UavSlot,
|
||||
D3D11UnorderedAccessView* pUav,
|
||||
UINT CtrSlot,
|
||||
UINT Counter);
|
||||
|
||||
VkClearValue ConvertColorValue(
|
||||
const FLOAT Color[4],
|
||||
const DxvkFormatInfo* pFormatInfo);
|
||||
|
||||
void CopyBuffer(
|
||||
D3D11Buffer* pDstBuffer,
|
||||
VkDeviceSize DstOffset,
|
||||
@ -787,74 +887,134 @@ namespace dxvk {
|
||||
VkOffset3D SrcOffset,
|
||||
VkExtent3D SrcExtent);
|
||||
|
||||
void CopyTiledResourceData(
|
||||
ID3D11Resource* pResource,
|
||||
const D3D11_TILED_RESOURCE_COORDINATE* pRegionCoordinate,
|
||||
const D3D11_TILE_REGION_SIZE* pRegionSize,
|
||||
DxvkBufferSlice BufferSlice,
|
||||
UINT Flags);
|
||||
|
||||
void DiscardBuffer(
|
||||
ID3D11Resource* pResource);
|
||||
|
||||
|
||||
void DiscardTexture(
|
||||
ID3D11Resource* pResource,
|
||||
UINT Subresource);
|
||||
|
||||
template<typename ContextType>
|
||||
static void UpdateResource(
|
||||
ContextType* pContext,
|
||||
ID3D11Resource* pDstResource,
|
||||
UINT DstSubresource,
|
||||
const D3D11_BOX* pDstBox,
|
||||
const void* pSrcData,
|
||||
UINT SrcRowPitch,
|
||||
UINT SrcDepthPitch,
|
||||
UINT CopyFlags) {
|
||||
D3D10DeviceLock lock = pContext->LockContext();
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void GetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppConstantBuffers,
|
||||
UINT* pFirstConstant,
|
||||
UINT* pNumConstants);
|
||||
|
||||
if (!pDstResource)
|
||||
return;
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void GetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView** ppShaderResourceViews);
|
||||
|
||||
// We need a different code path for buffers
|
||||
D3D11_RESOURCE_DIMENSION resourceType;
|
||||
pDstResource->GetType(&resourceType);
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void GetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState** ppSamplers);
|
||||
|
||||
if (likely(resourceType == D3D11_RESOURCE_DIMENSION_BUFFER)) {
|
||||
const auto bufferResource = static_cast<D3D11Buffer*>(pDstResource);
|
||||
uint64_t bufferSize = bufferResource->Desc()->ByteWidth;
|
||||
DxvkGlobalPipelineBarrier GetTiledResourceDependency(
|
||||
ID3D11DeviceChild* pObject);
|
||||
|
||||
// Provide a fast path for mapped buffer updates since some
|
||||
// games use UpdateSubresource to update constant buffers.
|
||||
if (likely(bufferResource->GetMapMode() == D3D11_COMMON_BUFFER_MAP_MODE_DIRECT) && likely(!pDstBox)) {
|
||||
pContext->UpdateMappedBuffer(bufferResource, 0, bufferSize, pSrcData, 0);
|
||||
return;
|
||||
}
|
||||
D3D11MaxUsedBindings GetMaxUsedBindings();
|
||||
|
||||
// Validate buffer range to update
|
||||
uint64_t offset = 0;
|
||||
uint64_t length = bufferSize;
|
||||
void ResetCommandListState();
|
||||
|
||||
if (pDstBox) {
|
||||
offset = pDstBox->left;
|
||||
length = pDstBox->right - offset;
|
||||
}
|
||||
void ResetContextState();
|
||||
|
||||
if (unlikely(offset + length > bufferSize))
|
||||
return;
|
||||
void ResetStagingBuffer();
|
||||
|
||||
// Still try to be fast if a box is provided but we update the full buffer
|
||||
if (likely(bufferResource->GetMapMode() == D3D11_COMMON_BUFFER_MAP_MODE_DIRECT)) {
|
||||
CopyFlags &= D3D11_COPY_DISCARD | D3D11_COPY_NO_OVERWRITE;
|
||||
template<DxbcProgramType ShaderStage, typename T>
|
||||
void ResolveSrvHazards(
|
||||
T* pView);
|
||||
|
||||
if (likely(length == bufferSize) || unlikely(CopyFlags != 0)) {
|
||||
pContext->UpdateMappedBuffer(bufferResource, offset, length, pSrcData, CopyFlags);
|
||||
return;
|
||||
}
|
||||
}
|
||||
template<typename T>
|
||||
void ResolveCsSrvHazards(
|
||||
T* pView);
|
||||
|
||||
// Otherwise we can't really do anything fancy, so just do a GPU copy
|
||||
pContext->UpdateBuffer(bufferResource, offset, length, pSrcData);
|
||||
} else {
|
||||
D3D11CommonTexture* textureResource = GetCommonTexture(pDstResource);
|
||||
template<typename T>
|
||||
void ResolveOmSrvHazards(
|
||||
T* pView);
|
||||
|
||||
pContext->UpdateTexture(textureResource,
|
||||
DstSubresource, pDstBox, pSrcData, SrcRowPitch, SrcDepthPitch);
|
||||
}
|
||||
}
|
||||
bool ResolveOmRtvHazards(
|
||||
D3D11UnorderedAccessView* pView);
|
||||
|
||||
void ResolveOmUavHazards(
|
||||
D3D11RenderTargetView* pView);
|
||||
|
||||
void RestoreCommandListState();
|
||||
|
||||
template<DxbcProgramType Stage>
|
||||
void RestoreConstantBuffers();
|
||||
|
||||
template<DxbcProgramType Stage>
|
||||
void RestoreSamplers();
|
||||
|
||||
template<DxbcProgramType Stage>
|
||||
void RestoreShaderResources();
|
||||
|
||||
template<DxbcProgramType Stage>
|
||||
void RestoreUnorderedAccessViews();
|
||||
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void SetConstantBuffers(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers);
|
||||
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void SetConstantBuffers1(
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers,
|
||||
const UINT* pFirstConstant,
|
||||
const UINT* pNumConstants);
|
||||
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void SetShaderResources(
|
||||
UINT StartSlot,
|
||||
UINT NumResources,
|
||||
ID3D11ShaderResourceView* const* ppResources);
|
||||
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void SetSamplers(
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState* const* ppSamplers);
|
||||
|
||||
void SetRenderTargetsAndUnorderedAccessViews(
|
||||
UINT NumRTVs,
|
||||
ID3D11RenderTargetView* const* ppRenderTargetViews,
|
||||
ID3D11DepthStencilView* pDepthStencilView,
|
||||
UINT UAVStartSlot,
|
||||
UINT NumUAVs,
|
||||
ID3D11UnorderedAccessView* const* ppUnorderedAccessViews,
|
||||
const UINT* pUAVInitialCounts);
|
||||
|
||||
void SetDrawBuffers(
|
||||
ID3D11Buffer* pBufferForArgs,
|
||||
ID3D11Buffer* pBufferForCount);
|
||||
|
||||
bool TestRtvUavHazards(
|
||||
UINT NumRTVs,
|
||||
ID3D11RenderTargetView* const* ppRTVs,
|
||||
UINT NumUAVs,
|
||||
ID3D11UnorderedAccessView* const* ppUAVs);
|
||||
|
||||
template<DxbcProgramType ShaderStage>
|
||||
bool TestSrvHazards(
|
||||
D3D11ShaderResourceView* pView);
|
||||
|
||||
void TrackResourceSequenceNumber(
|
||||
ID3D11Resource* pResource);
|
||||
|
||||
void UpdateBuffer(
|
||||
D3D11Buffer* pDstBuffer,
|
||||
@ -877,127 +1037,20 @@ namespace dxvk {
|
||||
VkExtent3D DstExtent,
|
||||
DxvkBufferSlice StagingBuffer);
|
||||
|
||||
void SetDrawBuffers(
|
||||
ID3D11Buffer* pBufferForArgs,
|
||||
ID3D11Buffer* pBufferForCount);
|
||||
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void SetConstantBuffers(
|
||||
D3D11ConstantBufferBindings& Bindings,
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers);
|
||||
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void SetConstantBuffers1(
|
||||
D3D11ConstantBufferBindings& Bindings,
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer* const* ppConstantBuffers,
|
||||
const UINT* pFirstConstant,
|
||||
const UINT* pNumConstants);
|
||||
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void SetSamplers(
|
||||
D3D11SamplerBindings& Bindings,
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState* const* ppSamplers);
|
||||
|
||||
template<DxbcProgramType ShaderStage>
|
||||
void SetShaderResources(
|
||||
D3D11ShaderResourceBindings& Bindings,
|
||||
UINT StartSlot,
|
||||
UINT NumResources,
|
||||
ID3D11ShaderResourceView* const* ppResources);
|
||||
|
||||
void GetConstantBuffers(
|
||||
const D3D11ConstantBufferBindings& Bindings,
|
||||
UINT StartSlot,
|
||||
UINT NumBuffers,
|
||||
ID3D11Buffer** ppConstantBuffers,
|
||||
UINT* pFirstConstant,
|
||||
UINT* pNumConstants);
|
||||
void UpdateResource(
|
||||
ID3D11Resource* pDstResource,
|
||||
UINT DstSubresource,
|
||||
const D3D11_BOX* pDstBox,
|
||||
const void* pSrcData,
|
||||
UINT SrcRowPitch,
|
||||
UINT SrcDepthPitch,
|
||||
UINT CopyFlags);
|
||||
|
||||
void GetShaderResources(
|
||||
const D3D11ShaderResourceBindings& Bindings,
|
||||
UINT StartSlot,
|
||||
UINT NumViews,
|
||||
ID3D11ShaderResourceView** ppShaderResourceViews);
|
||||
|
||||
void GetSamplers(
|
||||
const D3D11SamplerBindings& Bindings,
|
||||
UINT StartSlot,
|
||||
UINT NumSamplers,
|
||||
ID3D11SamplerState** ppSamplers);
|
||||
|
||||
void ResetState();
|
||||
|
||||
void RestoreState();
|
||||
|
||||
template<DxbcProgramType Stage>
|
||||
void RestoreConstantBuffers(
|
||||
D3D11ConstantBufferBindings& Bindings);
|
||||
|
||||
template<DxbcProgramType Stage>
|
||||
void RestoreSamplers(
|
||||
D3D11SamplerBindings& Bindings);
|
||||
|
||||
template<DxbcProgramType Stage>
|
||||
void RestoreShaderResources(
|
||||
D3D11ShaderResourceBindings& Bindings);
|
||||
|
||||
template<DxbcProgramType Stage>
|
||||
void RestoreUnorderedAccessViews(
|
||||
D3D11UnorderedAccessBindings& Bindings);
|
||||
|
||||
bool TestRtvUavHazards(
|
||||
UINT NumRTVs,
|
||||
ID3D11RenderTargetView* const* ppRTVs,
|
||||
UINT NumUAVs,
|
||||
ID3D11UnorderedAccessView* const* ppUAVs);
|
||||
|
||||
template<DxbcProgramType ShaderStage>
|
||||
bool TestSrvHazards(
|
||||
D3D11ShaderResourceView* pView);
|
||||
|
||||
template<DxbcProgramType ShaderStage, typename T>
|
||||
void ResolveSrvHazards(
|
||||
T* pView,
|
||||
D3D11ShaderResourceBindings& Bindings);
|
||||
|
||||
template<typename T>
|
||||
void ResolveCsSrvHazards(
|
||||
T* pView);
|
||||
|
||||
template<typename T>
|
||||
void ResolveOmSrvHazards(
|
||||
T* pView);
|
||||
|
||||
bool ResolveOmRtvHazards(
|
||||
D3D11UnorderedAccessView* pView);
|
||||
|
||||
void ResolveOmUavHazards(
|
||||
D3D11RenderTargetView* pView);
|
||||
|
||||
bool ValidateRenderTargets(
|
||||
UINT NumViews,
|
||||
ID3D11RenderTargetView* const* ppRenderTargetViews,
|
||||
ID3D11DepthStencilView* pDepthStencilView);
|
||||
|
||||
VkClearValue ConvertColorValue(
|
||||
const FLOAT Color[4],
|
||||
const DxvkFormatInfo* pFormatInfo);
|
||||
|
||||
DxvkDataSlice AllocUpdateBufferSlice(size_t Size);
|
||||
|
||||
DxvkBufferSlice AllocStagingBuffer(
|
||||
VkDeviceSize Size);
|
||||
|
||||
void ResetStagingBuffer();
|
||||
|
||||
DxvkCsChunkRef AllocCsChunk();
|
||||
|
||||
static void InitDefaultPrimitiveTopology(
|
||||
DxvkInputAssemblyState* pIaState);
|
||||
|
||||
@ -1013,6 +1066,51 @@ namespace dxvk {
|
||||
DxvkMultisampleState* pMsState,
|
||||
UINT SampleMask);
|
||||
|
||||
template<bool AllowFlush = !IsDeferred, typename Cmd>
|
||||
void EmitCs(Cmd&& command) {
|
||||
m_cmdData = nullptr;
|
||||
|
||||
if (unlikely(!m_csChunk->push(command))) {
|
||||
GetTypedContext()->EmitCsChunk(std::move(m_csChunk));
|
||||
m_csChunk = AllocCsChunk();
|
||||
|
||||
if constexpr (AllowFlush)
|
||||
GetTypedContext()->ConsiderFlush(GpuFlushType::ImplicitWeakHint);
|
||||
|
||||
m_csChunk->push(command);
|
||||
}
|
||||
}
|
||||
|
||||
template<typename M, bool AllowFlush = !IsDeferred, typename Cmd, typename... Args>
|
||||
M* EmitCsCmd(Cmd&& command, Args&&... args) {
|
||||
M* data = m_csChunk->pushCmd<M, Cmd, Args...>(
|
||||
command, std::forward<Args>(args)...);
|
||||
|
||||
if (unlikely(!data)) {
|
||||
GetTypedContext()->EmitCsChunk(std::move(m_csChunk));
|
||||
m_csChunk = AllocCsChunk();
|
||||
|
||||
if constexpr (AllowFlush)
|
||||
GetTypedContext()->ConsiderFlush(GpuFlushType::ImplicitWeakHint);
|
||||
|
||||
// We must record this command after the potential
|
||||
// flush since the caller may still access the data
|
||||
data = m_csChunk->pushCmd<M, Cmd, Args...>(
|
||||
command, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
m_cmdData = data;
|
||||
return data;
|
||||
}
|
||||
|
||||
void FlushCsChunk() {
|
||||
if (likely(!m_csChunk->empty())) {
|
||||
GetTypedContext()->EmitCsChunk(std::move(m_csChunk));
|
||||
m_csChunk = AllocCsChunk();
|
||||
m_cmdData = nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
const D3D11CommonShader* GetCommonShader(T* pShader) const {
|
||||
return pShader != nullptr ? pShader->GetCommonShader() : nullptr;
|
||||
@ -1034,55 +1132,16 @@ namespace dxvk {
|
||||
|
||||
return bufferSize >= Offset + Size;
|
||||
}
|
||||
|
||||
template<typename Cmd>
|
||||
void EmitCs(Cmd&& command) {
|
||||
m_cmdData = nullptr;
|
||||
|
||||
if (unlikely(!m_csChunk->push(command))) {
|
||||
EmitCsChunk(std::move(m_csChunk));
|
||||
|
||||
m_csChunk = AllocCsChunk();
|
||||
m_csChunk->push(command);
|
||||
}
|
||||
private:
|
||||
|
||||
ContextType* GetTypedContext() {
|
||||
return static_cast<ContextType*>(this);
|
||||
}
|
||||
|
||||
template<typename M, typename Cmd, typename... Args>
|
||||
M* EmitCsCmd(Cmd&& command, Args&&... args) {
|
||||
M* data = m_csChunk->pushCmd<M, Cmd, Args...>(
|
||||
command, std::forward<Args>(args)...);
|
||||
|
||||
if (unlikely(!data)) {
|
||||
EmitCsChunk(std::move(m_csChunk));
|
||||
|
||||
m_csChunk = AllocCsChunk();
|
||||
data = m_csChunk->pushCmd<M, Cmd, Args...>(
|
||||
command, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
m_cmdData = data;
|
||||
return data;
|
||||
D3D10DeviceLock LockContext() {
|
||||
return GetTypedContext()->LockContext();
|
||||
}
|
||||
|
||||
void FlushCsChunk() {
|
||||
if (likely(!m_csChunk->empty())) {
|
||||
EmitCsChunk(std::move(m_csChunk));
|
||||
m_csChunk = AllocCsChunk();
|
||||
m_cmdData = nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
void TrackResourceSequenceNumber(
|
||||
ID3D11Resource* pResource);
|
||||
|
||||
virtual void EmitCsChunk(DxvkCsChunkRef&& chunk) = 0;
|
||||
|
||||
virtual void TrackTextureSequenceNumber(
|
||||
D3D11CommonTexture* pResource,
|
||||
UINT Subresource) = 0;
|
||||
|
||||
virtual void TrackBufferSequenceNumber(
|
||||
D3D11Buffer* pResource) = 0;
|
||||
|
||||
};
|
||||
|
||||
|
@ -7,20 +7,9 @@ namespace dxvk {
|
||||
D3D11Device* pParent,
|
||||
const Rc<DxvkDevice>& Device,
|
||||
UINT ContextFlags)
|
||||
: D3D11DeviceContext(pParent, Device, GetCsChunkFlags(pParent)),
|
||||
m_contextFlags(ContextFlags),
|
||||
: D3D11CommonContext<D3D11DeferredContext>(pParent, Device, ContextFlags, GetCsChunkFlags(pParent)),
|
||||
m_commandList (CreateCommandList()) {
|
||||
ClearState();
|
||||
}
|
||||
|
||||
|
||||
D3D11_DEVICE_CONTEXT_TYPE STDMETHODCALLTYPE D3D11DeferredContext::GetType() {
|
||||
return D3D11_DEVICE_CONTEXT_DEFERRED;
|
||||
}
|
||||
|
||||
|
||||
UINT STDMETHODCALLTYPE D3D11DeferredContext::GetContextFlags() {
|
||||
return m_contextFlags;
|
||||
ResetContextState();
|
||||
}
|
||||
|
||||
|
||||
@ -146,14 +135,26 @@ namespace dxvk {
|
||||
BOOL RestoreContextState) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
// Clear state so that the command list can't observe any
|
||||
// current context state. The command list itself will clean
|
||||
// up after execution to ensure that no state changes done
|
||||
// by the command list are visible to the immediate context.
|
||||
ResetCommandListState();
|
||||
|
||||
// Flush any outstanding commands so that
|
||||
// we don't mess up the execution order
|
||||
FlushCsChunk();
|
||||
|
||||
static_cast<D3D11CommandList*>(pCommandList)->EmitToCommandList(m_commandList.ptr());
|
||||
// Record any chunks from the given command list into the
|
||||
// current command list and deal with context state
|
||||
auto commandList = static_cast<D3D11CommandList*>(pCommandList);
|
||||
m_chunkId = m_commandList->AddCommandList(commandList);
|
||||
|
||||
// Restore deferred context state
|
||||
if (RestoreContextState)
|
||||
RestoreState();
|
||||
RestoreCommandListState();
|
||||
else
|
||||
ClearState();
|
||||
ResetContextState();
|
||||
}
|
||||
|
||||
|
||||
@ -162,17 +163,31 @@ namespace dxvk {
|
||||
ID3D11CommandList **ppCommandList) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
// End all queries that were left active by the app
|
||||
FinalizeQueries();
|
||||
|
||||
// Clean up command list state so that the any state changed
|
||||
// by this command list does not affect the calling context.
|
||||
// This also ensures that the command list is never empty.
|
||||
ResetCommandListState();
|
||||
|
||||
// Make sure all commands are visible to the command list
|
||||
FlushCsChunk();
|
||||
|
||||
if (ppCommandList != nullptr)
|
||||
if (ppCommandList)
|
||||
*ppCommandList = m_commandList.ref();
|
||||
|
||||
// Create a clean command list, and if requested, restore all
|
||||
// previously set context state. Otherwise, reset the context.
|
||||
// Any use of ExecuteCommandList will reset command list state
|
||||
// before the command list is actually executed.
|
||||
m_commandList = CreateCommandList();
|
||||
m_chunkId = 0;
|
||||
|
||||
if (RestoreDeferredContextState)
|
||||
RestoreState();
|
||||
RestoreCommandListState();
|
||||
else
|
||||
ClearState();
|
||||
ResetContextState();
|
||||
|
||||
m_mappedResources.clear();
|
||||
ResetStagingBuffer();
|
||||
@ -236,31 +251,6 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeferredContext::UpdateSubresource(
|
||||
ID3D11Resource* pDstResource,
|
||||
UINT DstSubresource,
|
||||
const D3D11_BOX* pDstBox,
|
||||
const void* pSrcData,
|
||||
UINT SrcRowPitch,
|
||||
UINT SrcDepthPitch) {
|
||||
UpdateResource<D3D11DeferredContext>(this, pDstResource,
|
||||
DstSubresource, pDstBox, pSrcData, SrcRowPitch, SrcDepthPitch, 0);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeferredContext::UpdateSubresource1(
|
||||
ID3D11Resource* pDstResource,
|
||||
UINT DstSubresource,
|
||||
const D3D11_BOX* pDstBox,
|
||||
const void* pSrcData,
|
||||
UINT SrcRowPitch,
|
||||
UINT SrcDepthPitch,
|
||||
UINT CopyFlags) {
|
||||
UpdateResource<D3D11DeferredContext>(this, pDstResource,
|
||||
DstSubresource, pDstBox, pSrcData, SrcRowPitch, SrcDepthPitch, CopyFlags);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeferredContext::SwapDeviceContextState(
|
||||
ID3DDeviceContextState* pState,
|
||||
ID3DDeviceContextState** ppPreviousState) {
|
||||
@ -333,7 +323,7 @@ namespace dxvk {
|
||||
|
||||
VkFormat packedFormat = pTexture->GetPackedFormat();
|
||||
|
||||
auto formatInfo = imageFormatInfo(packedFormat);
|
||||
auto formatInfo = lookupFormatInfo(packedFormat);
|
||||
auto subresource = pTexture->GetSubresourceFromIndex(
|
||||
formatInfo->aspectMask, Subresource);
|
||||
|
||||
@ -396,12 +386,17 @@ namespace dxvk {
|
||||
|
||||
|
||||
Com<D3D11CommandList> D3D11DeferredContext::CreateCommandList() {
|
||||
return new D3D11CommandList(m_parent, m_contextFlags);
|
||||
return new D3D11CommandList(m_parent, m_flags);
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeferredContext::EmitCsChunk(DxvkCsChunkRef&& chunk) {
|
||||
m_commandList->AddChunk(std::move(chunk));
|
||||
m_chunkId = m_commandList->AddChunk(std::move(chunk));
|
||||
}
|
||||
|
||||
|
||||
uint64_t D3D11DeferredContext::GetCurrentChunkId() const {
|
||||
return m_csChunk->empty() ? m_chunkId : m_chunkId + 1;
|
||||
}
|
||||
|
||||
|
||||
@ -411,14 +406,15 @@ namespace dxvk {
|
||||
m_commandList->TrackResourceUsage(
|
||||
pResource->GetInterface(),
|
||||
pResource->GetDimension(),
|
||||
Subresource);
|
||||
Subresource, GetCurrentChunkId());
|
||||
}
|
||||
|
||||
|
||||
void D3D11DeferredContext::TrackBufferSequenceNumber(
|
||||
D3D11Buffer* pResource) {
|
||||
m_commandList->TrackResourceUsage(
|
||||
pResource, D3D11_RESOURCE_DIMENSION_BUFFER, 0);
|
||||
m_commandList->TrackResourceUsage(pResource,
|
||||
D3D11_RESOURCE_DIMENSION_BUFFER, 0,
|
||||
GetCurrentChunkId());
|
||||
}
|
||||
|
||||
|
||||
|
@ -1,9 +1,7 @@
|
||||
#pragma once
|
||||
|
||||
#include "d3d11_buffer.h"
|
||||
#include "d3d11_cmdlist.h"
|
||||
#include "d3d11_context.h"
|
||||
#include "d3d11_texture.h"
|
||||
|
||||
#include <vector>
|
||||
|
||||
@ -23,8 +21,8 @@ namespace dxvk {
|
||||
D3D11_MAPPED_SUBRESOURCE MapInfo;
|
||||
};
|
||||
|
||||
class D3D11DeferredContext : public D3D11DeviceContext {
|
||||
friend class D3D11DeviceContext;
|
||||
class D3D11DeferredContext : public D3D11CommonContext<D3D11DeferredContext> {
|
||||
friend class D3D11CommonContext<D3D11DeferredContext>;
|
||||
public:
|
||||
|
||||
D3D11DeferredContext(
|
||||
@ -32,10 +30,6 @@ namespace dxvk {
|
||||
const Rc<DxvkDevice>& Device,
|
||||
UINT ContextFlags);
|
||||
|
||||
D3D11_DEVICE_CONTEXT_TYPE STDMETHODCALLTYPE GetType();
|
||||
|
||||
UINT STDMETHODCALLTYPE GetContextFlags();
|
||||
|
||||
HRESULT STDMETHODCALLTYPE GetData(
|
||||
ID3D11Asynchronous* pAsync,
|
||||
void* pData,
|
||||
@ -81,31 +75,16 @@ namespace dxvk {
|
||||
ID3D11Resource* pResource,
|
||||
UINT Subresource);
|
||||
|
||||
void STDMETHODCALLTYPE UpdateSubresource(
|
||||
ID3D11Resource* pDstResource,
|
||||
UINT DstSubresource,
|
||||
const D3D11_BOX* pDstBox,
|
||||
const void* pSrcData,
|
||||
UINT SrcRowPitch,
|
||||
UINT SrcDepthPitch);
|
||||
|
||||
void STDMETHODCALLTYPE UpdateSubresource1(
|
||||
ID3D11Resource* pDstResource,
|
||||
UINT DstSubresource,
|
||||
const D3D11_BOX* pDstBox,
|
||||
const void* pSrcData,
|
||||
UINT SrcRowPitch,
|
||||
UINT SrcDepthPitch,
|
||||
UINT CopyFlags);
|
||||
|
||||
void STDMETHODCALLTYPE SwapDeviceContextState(
|
||||
ID3DDeviceContextState* pState,
|
||||
ID3DDeviceContextState** ppPreviousState);
|
||||
|
||||
D3D10DeviceLock LockContext() {
|
||||
return D3D10DeviceLock();
|
||||
}
|
||||
|
||||
private:
|
||||
|
||||
const UINT m_contextFlags;
|
||||
|
||||
// Command list that we're recording
|
||||
Com<D3D11CommandList> m_commandList;
|
||||
|
||||
@ -117,6 +96,9 @@ namespace dxvk {
|
||||
// Begun and ended queries, will also be stored in command list
|
||||
std::vector<Com<D3D11Query, false>> m_queriesBegun;
|
||||
|
||||
// Chunk ID within the current command list
|
||||
uint64_t m_chunkId = 0ull;
|
||||
|
||||
HRESULT MapBuffer(
|
||||
ID3D11Resource* pResource,
|
||||
D3D11_MAPPED_SUBRESOURCE* pMappedResource);
|
||||
@ -139,6 +121,8 @@ namespace dxvk {
|
||||
|
||||
void EmitCsChunk(DxvkCsChunkRef&& chunk);
|
||||
|
||||
uint64_t GetCurrentChunkId() const;
|
||||
|
||||
void TrackTextureSequenceNumber(
|
||||
D3D11CommonTexture* pResource,
|
||||
UINT Subresource);
|
||||
|
@ -3,38 +3,44 @@
|
||||
#include <cstring>
|
||||
|
||||
#include "d3d11_device.h"
|
||||
#include "d3d11_context.h"
|
||||
#include "d3d11_context_imm.h"
|
||||
#include "d3d11_context_def.h"
|
||||
#include "d3d11_cuda.h"
|
||||
|
||||
#include "../util/log/log.h"
|
||||
|
||||
namespace dxvk {
|
||||
|
||||
D3D11DeviceContextExt::D3D11DeviceContextExt(
|
||||
D3D11DeviceContext* pContext)
|
||||
template<typename ContextType>
|
||||
D3D11DeviceContextExt<ContextType>::D3D11DeviceContextExt(
|
||||
ContextType* pContext)
|
||||
: m_ctx(pContext) {
|
||||
|
||||
}
|
||||
|
||||
|
||||
ULONG STDMETHODCALLTYPE D3D11DeviceContextExt::AddRef() {
|
||||
template<typename ContextType>
|
||||
ULONG STDMETHODCALLTYPE D3D11DeviceContextExt<ContextType>::AddRef() {
|
||||
return m_ctx->AddRef();
|
||||
}
|
||||
|
||||
|
||||
ULONG STDMETHODCALLTYPE D3D11DeviceContextExt::Release() {
|
||||
template<typename ContextType>
|
||||
ULONG STDMETHODCALLTYPE D3D11DeviceContextExt<ContextType>::Release() {
|
||||
return m_ctx->Release();
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D11DeviceContextExt::QueryInterface(
|
||||
template<typename ContextType>
|
||||
HRESULT STDMETHODCALLTYPE D3D11DeviceContextExt<ContextType>::QueryInterface(
|
||||
REFIID riid,
|
||||
void** ppvObject) {
|
||||
return m_ctx->QueryInterface(riid, ppvObject);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContextExt::MultiDrawIndirect(
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11DeviceContextExt<ContextType>::MultiDrawIndirect(
|
||||
UINT DrawCount,
|
||||
ID3D11Buffer* pBufferForArgs,
|
||||
UINT ByteOffsetForArgs,
|
||||
@ -52,7 +58,8 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContextExt::MultiDrawIndexedIndirect(
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11DeviceContextExt<ContextType>::MultiDrawIndexedIndirect(
|
||||
UINT DrawCount,
|
||||
ID3D11Buffer* pBufferForArgs,
|
||||
UINT ByteOffsetForArgs,
|
||||
@ -70,7 +77,8 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContextExt::MultiDrawIndirectCount(
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11DeviceContextExt<ContextType>::MultiDrawIndirectCount(
|
||||
UINT MaxDrawCount,
|
||||
ID3D11Buffer* pBufferForCount,
|
||||
UINT ByteOffsetForCount,
|
||||
@ -91,7 +99,8 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContextExt::MultiDrawIndexedIndirectCount(
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11DeviceContextExt<ContextType>::MultiDrawIndexedIndirectCount(
|
||||
UINT MaxDrawCount,
|
||||
ID3D11Buffer* pBufferForCount,
|
||||
UINT ByteOffsetForCount,
|
||||
@ -112,7 +121,8 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContextExt::SetDepthBoundsTest(
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11DeviceContextExt<ContextType>::SetDepthBoundsTest(
|
||||
BOOL Enable,
|
||||
FLOAT MinDepthBounds,
|
||||
FLOAT MaxDepthBounds) {
|
||||
@ -129,7 +139,8 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11DeviceContextExt::SetBarrierControl(
|
||||
template<typename ContextType>
|
||||
void STDMETHODCALLTYPE D3D11DeviceContextExt<ContextType>::SetBarrierControl(
|
||||
UINT ControlFlags) {
|
||||
D3D10DeviceLock lock = m_ctx->LockContext();
|
||||
DxvkBarrierControlFlags flags;
|
||||
@ -146,7 +157,8 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
bool STDMETHODCALLTYPE D3D11DeviceContextExt::LaunchCubinShaderNVX(IUnknown* hShader, uint32_t GridX, uint32_t GridY, uint32_t GridZ,
|
||||
template<typename ContextType>
|
||||
bool STDMETHODCALLTYPE D3D11DeviceContextExt<ContextType>::LaunchCubinShaderNVX(IUnknown* hShader, uint32_t GridX, uint32_t GridY, uint32_t GridZ,
|
||||
const void* pParams, uint32_t ParamSize, void* const* pReadResources, uint32_t NumReadResources, void* const* pWriteResources, uint32_t NumWriteResources) {
|
||||
D3D10DeviceLock lock = m_ctx->LockContext();
|
||||
|
||||
@ -202,4 +214,9 @@ namespace dxvk {
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
template class D3D11DeviceContextExt<D3D11DeferredContext>;
|
||||
template class D3D11DeviceContextExt<D3D11ImmediateContext>;
|
||||
|
||||
}
|
||||
|
@ -4,14 +4,16 @@
|
||||
|
||||
namespace dxvk {
|
||||
|
||||
class D3D11DeviceContext;
|
||||
class D3D11DeferredContext;
|
||||
class D3D11ImmediateContext;
|
||||
|
||||
template<typename ContextType>
|
||||
class D3D11DeviceContextExt : public ID3D11VkExtContext1 {
|
||||
|
||||
public:
|
||||
|
||||
D3D11DeviceContextExt(
|
||||
D3D11DeviceContext* pContext);
|
||||
ContextType* pContext);
|
||||
|
||||
ULONG STDMETHODCALLTYPE AddRef();
|
||||
|
||||
@ -71,7 +73,7 @@ namespace dxvk {
|
||||
|
||||
private:
|
||||
|
||||
D3D11DeviceContext* m_ctx;
|
||||
ContextType* m_ctx;
|
||||
|
||||
};
|
||||
|
||||
|
@ -1,8 +1,11 @@
|
||||
#include "d3d11_cmdlist.h"
|
||||
#include "d3d11_context_imm.h"
|
||||
#include "d3d11_device.h"
|
||||
#include "d3d11_fence.h"
|
||||
#include "d3d11_texture.h"
|
||||
|
||||
#include "../util/util_win32_compat.h"
|
||||
|
||||
constexpr static uint32_t MinFlushIntervalUs = 750;
|
||||
constexpr static uint32_t IncFlushIntervalUs = 250;
|
||||
constexpr static uint32_t MaxPendingSubmits = 6;
|
||||
@ -12,9 +15,11 @@ namespace dxvk {
|
||||
D3D11ImmediateContext::D3D11ImmediateContext(
|
||||
D3D11Device* pParent,
|
||||
const Rc<DxvkDevice>& Device)
|
||||
: D3D11DeviceContext(pParent, Device, DxvkCsChunkFlag::SingleUse),
|
||||
m_csThread(Device, Device->createContext()),
|
||||
: D3D11CommonContext<D3D11ImmediateContext>(pParent, Device, 0, DxvkCsChunkFlag::SingleUse),
|
||||
m_csThread(Device, Device->createContext(DxvkContextType::Primary)),
|
||||
m_maxImplicitDiscardSize(pParent->GetOptions()->maxImplicitDiscardSize),
|
||||
m_submissionFence(new sync::CallbackFence()),
|
||||
m_multithread(this, false, pParent->GetOptions()->enableContextLock),
|
||||
m_videoContext(this, Device) {
|
||||
EmitCs([
|
||||
cDevice = m_device,
|
||||
@ -39,32 +44,32 @@ namespace dxvk {
|
||||
|
||||
|
||||
D3D11ImmediateContext::~D3D11ImmediateContext() {
|
||||
Flush();
|
||||
// Avoids hanging when in this state, see comment
|
||||
// in DxvkDevice::~DxvkDevice.
|
||||
if (this_thread::isInModuleDetachment())
|
||||
return;
|
||||
|
||||
ExecuteFlush(GpuFlushType::ExplicitFlush, nullptr, true);
|
||||
SynchronizeCsThread(DxvkCsThread::SynchronizeAll);
|
||||
SynchronizeDevice();
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D11ImmediateContext::QueryInterface(REFIID riid, void** ppvObject) {
|
||||
if (riid == __uuidof(ID3D10Multithread)) {
|
||||
*ppvObject = ref(&m_multithread);
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
if (riid == __uuidof(ID3D11VideoContext)) {
|
||||
*ppvObject = ref(&m_videoContext);
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
return D3D11DeviceContext::QueryInterface(riid, ppvObject);
|
||||
return D3D11CommonContext<D3D11ImmediateContext>::QueryInterface(riid, ppvObject);
|
||||
}
|
||||
|
||||
|
||||
D3D11_DEVICE_CONTEXT_TYPE STDMETHODCALLTYPE D3D11ImmediateContext::GetType() {
|
||||
return D3D11_DEVICE_CONTEXT_IMMEDIATE;
|
||||
}
|
||||
|
||||
|
||||
UINT STDMETHODCALLTYPE D3D11ImmediateContext::GetContextFlags() {
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D11ImmediateContext::GetData(
|
||||
ID3D11Asynchronous* pAsync,
|
||||
void* pData,
|
||||
@ -95,7 +100,8 @@ namespace dxvk {
|
||||
|
||||
// Ignore the DONOTFLUSH flag here as some games will spin
|
||||
// on queries without ever flushing the context otherwise.
|
||||
FlushImplicit(FALSE);
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
ConsiderFlush(GpuFlushType::ImplicitSynchronization);
|
||||
}
|
||||
|
||||
return hr;
|
||||
@ -144,57 +150,69 @@ namespace dxvk {
|
||||
query->NotifyEnd();
|
||||
|
||||
if (query->IsStalling())
|
||||
Flush();
|
||||
ExecuteFlush(GpuFlushType::ImplicitSynchronization, nullptr, false);
|
||||
else if (query->IsEvent())
|
||||
FlushImplicit(TRUE);
|
||||
ConsiderFlush(GpuFlushType::ImplicitStrongHint);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11ImmediateContext::Flush() {
|
||||
Flush1(D3D11_CONTEXT_TYPE_ALL, nullptr);
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
ExecuteFlush(GpuFlushType::ExplicitFlush, nullptr, true);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11ImmediateContext::Flush1(
|
||||
D3D11_CONTEXT_TYPE ContextType,
|
||||
HANDLE hEvent) {
|
||||
m_parent->FlushInitContext();
|
||||
|
||||
if (hEvent)
|
||||
SignalEvent(hEvent);
|
||||
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
if (m_csIsBusy || !m_csChunk->empty()) {
|
||||
// Add commands to flush the threaded
|
||||
// context, then flush the command list
|
||||
EmitCs([] (DxvkContext* ctx) {
|
||||
ctx->flushCommandList();
|
||||
});
|
||||
|
||||
FlushCsChunk();
|
||||
|
||||
// Reset flush timer used for implicit flushes
|
||||
m_lastFlush = dxvk::high_resolution_clock::now();
|
||||
m_csIsBusy = false;
|
||||
}
|
||||
|
||||
ExecuteFlush(GpuFlushType::ExplicitFlush, hEvent, true);
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D11ImmediateContext::Signal(
|
||||
ID3D11Fence* pFence,
|
||||
UINT64 Value) {
|
||||
Logger::err("D3D11ImmediateContext::Signal: Not implemented");
|
||||
return E_NOTIMPL;
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
auto fence = static_cast<D3D11Fence*>(pFence);
|
||||
|
||||
if (!fence)
|
||||
return E_INVALIDARG;
|
||||
|
||||
EmitCs([
|
||||
cFence = fence->GetFence(),
|
||||
cValue = Value
|
||||
] (DxvkContext* ctx) {
|
||||
ctx->signalFence(cFence, cValue);
|
||||
});
|
||||
|
||||
ExecuteFlush(GpuFlushType::ExplicitFlush, nullptr, true);
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D11ImmediateContext::Wait(
|
||||
ID3D11Fence* pFence,
|
||||
UINT64 Value) {
|
||||
Logger::err("D3D11ImmediateContext::Wait: Not implemented");
|
||||
return E_NOTIMPL;
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
auto fence = static_cast<D3D11Fence*>(pFence);
|
||||
|
||||
if (!fence)
|
||||
return E_INVALIDARG;
|
||||
|
||||
ExecuteFlush(GpuFlushType::ExplicitFlush, nullptr, true);
|
||||
|
||||
EmitCs([
|
||||
cFence = fence->GetFence(),
|
||||
cValue = Value
|
||||
] (DxvkContext* ctx) {
|
||||
ctx->waitFence(cFence, cValue);
|
||||
});
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
@ -205,27 +223,39 @@ namespace dxvk {
|
||||
|
||||
auto commandList = static_cast<D3D11CommandList*>(pCommandList);
|
||||
|
||||
// Clear state so that the command list can't observe any
|
||||
// current context state. The command list itself will clean
|
||||
// up after execution to ensure that no state changes done
|
||||
// by the command list are visible to the immediate context.
|
||||
ResetCommandListState();
|
||||
|
||||
// Flush any outstanding commands so that
|
||||
// we don't mess up the execution order
|
||||
FlushCsChunk();
|
||||
|
||||
// As an optimization, flush everything if the
|
||||
// number of pending draw calls is high enough.
|
||||
FlushImplicit(FALSE);
|
||||
|
||||
// Dispatch command list to the CS thread and
|
||||
// restore the immediate context's state
|
||||
uint64_t csSeqNum = commandList->EmitToCsThread(&m_csThread);
|
||||
m_csSeqNum = std::max(m_csSeqNum, csSeqNum);
|
||||
|
||||
ConsiderFlush(GpuFlushType::ImplicitWeakHint);
|
||||
|
||||
// Dispatch command list to the CS thread
|
||||
commandList->EmitToCsThread([this] (DxvkCsChunkRef&& chunk, GpuFlushType flushType) {
|
||||
EmitCsChunk(std::move(chunk));
|
||||
|
||||
// Return the sequence number from before the flush since
|
||||
// that is actually going to be needed for resource tracking
|
||||
uint64_t csSeqNum = m_csSeqNum;
|
||||
|
||||
// Consider a flush after every chunk in case the app
|
||||
// submits a very large command list or the GPU is idle
|
||||
ConsiderFlush(flushType);
|
||||
return csSeqNum;
|
||||
});
|
||||
|
||||
// Restore the immediate context's state
|
||||
if (RestoreContextState)
|
||||
RestoreState();
|
||||
RestoreCommandListState();
|
||||
else
|
||||
ClearState();
|
||||
|
||||
// Mark CS thread as busy so that subsequent
|
||||
// flush operations get executed correctly.
|
||||
m_csIsBusy = true;
|
||||
ResetContextState();
|
||||
}
|
||||
|
||||
|
||||
@ -290,59 +320,7 @@ namespace dxvk {
|
||||
}
|
||||
}
|
||||
|
||||
void STDMETHODCALLTYPE D3D11ImmediateContext::UpdateSubresource(
|
||||
ID3D11Resource* pDstResource,
|
||||
UINT DstSubresource,
|
||||
const D3D11_BOX* pDstBox,
|
||||
const void* pSrcData,
|
||||
UINT SrcRowPitch,
|
||||
UINT SrcDepthPitch) {
|
||||
UpdateResource<D3D11ImmediateContext>(this, pDstResource,
|
||||
DstSubresource, pDstBox, pSrcData, SrcRowPitch, SrcDepthPitch, 0);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11ImmediateContext::UpdateSubresource1(
|
||||
ID3D11Resource* pDstResource,
|
||||
UINT DstSubresource,
|
||||
const D3D11_BOX* pDstBox,
|
||||
const void* pSrcData,
|
||||
UINT SrcRowPitch,
|
||||
UINT SrcDepthPitch,
|
||||
UINT CopyFlags) {
|
||||
UpdateResource<D3D11ImmediateContext>(this, pDstResource,
|
||||
DstSubresource, pDstBox, pSrcData, SrcRowPitch, SrcDepthPitch, CopyFlags);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11ImmediateContext::OMSetRenderTargets(
|
||||
UINT NumViews,
|
||||
ID3D11RenderTargetView* const* ppRenderTargetViews,
|
||||
ID3D11DepthStencilView* pDepthStencilView) {
|
||||
FlushImplicit(TRUE);
|
||||
|
||||
D3D11DeviceContext::OMSetRenderTargets(
|
||||
NumViews, ppRenderTargetViews, pDepthStencilView);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11ImmediateContext::OMSetRenderTargetsAndUnorderedAccessViews(
|
||||
UINT NumRTVs,
|
||||
ID3D11RenderTargetView* const* ppRenderTargetViews,
|
||||
ID3D11DepthStencilView* pDepthStencilView,
|
||||
UINT UAVStartSlot,
|
||||
UINT NumUAVs,
|
||||
ID3D11UnorderedAccessView* const* ppUnorderedAccessViews,
|
||||
const UINT* pUAVInitialCounts) {
|
||||
FlushImplicit(TRUE);
|
||||
|
||||
D3D11DeviceContext::OMSetRenderTargetsAndUnorderedAccessViews(
|
||||
NumRTVs, ppRenderTargetViews, pDepthStencilView,
|
||||
UAVStartSlot, NumUAVs, ppUnorderedAccessViews,
|
||||
pUAVInitialCounts);
|
||||
}
|
||||
|
||||
|
||||
HRESULT D3D11ImmediateContext::MapBuffer(
|
||||
D3D11Buffer* pResource,
|
||||
D3D11_MAP MapType,
|
||||
@ -407,8 +385,6 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
if (doInvalidatePreserve) {
|
||||
FlushImplicit(TRUE);
|
||||
|
||||
auto prevSlice = pResource->GetMappedSlice();
|
||||
auto physSlice = pResource->DiscardSlice();
|
||||
|
||||
@ -472,7 +448,7 @@ namespace dxvk {
|
||||
|
||||
uint64_t sequenceNumber = pResource->GetSequenceNumber(Subresource);
|
||||
|
||||
auto formatInfo = imageFormatInfo(packedFormat);
|
||||
auto formatInfo = lookupFormatInfo(packedFormat);
|
||||
void* mapPtr;
|
||||
|
||||
if (mapMode == D3D11_COMMON_TEXTURE_MAP_MODE_DIRECT) {
|
||||
@ -495,6 +471,20 @@ namespace dxvk {
|
||||
constexpr uint32_t DoWait = (1u << 2);
|
||||
uint32_t doFlags;
|
||||
|
||||
if (mapMode == D3D11_COMMON_TEXTURE_MAP_MODE_BUFFER) {
|
||||
// If the image can be written by the GPU, we need to update the
|
||||
// mapped staging buffer to reflect the current image contents.
|
||||
if (pResource->Desc()->Usage == D3D11_USAGE_DEFAULT) {
|
||||
bool needsReadback = !pResource->NeedsDirtyRegionTracking();
|
||||
|
||||
needsReadback |= MapType == D3D11_MAP_READ
|
||||
|| MapType == D3D11_MAP_READ_WRITE;
|
||||
|
||||
if (needsReadback)
|
||||
ReadbackImageBuffer(pResource, Subresource);
|
||||
}
|
||||
}
|
||||
|
||||
if (MapType == D3D11_MAP_READ) {
|
||||
// Reads will not change the image content, so we only need
|
||||
// to wait for the GPU to finish writing to the mapped buffer.
|
||||
@ -540,8 +530,6 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
if (doFlags & DoInvalidate) {
|
||||
FlushImplicit(TRUE);
|
||||
|
||||
DxvkBufferSliceHandle prevSlice = pResource->GetMappedSlice(Subresource);
|
||||
DxvkBufferSliceHandle physSlice = pResource->DiscardSlice(Subresource);
|
||||
|
||||
@ -600,20 +588,116 @@ namespace dxvk {
|
||||
// the given subresource is actually mapped right now
|
||||
m_mappedImageCount -= 1;
|
||||
|
||||
if ((mapType != D3D11_MAP_READ) &&
|
||||
(pResource->GetMapMode() == D3D11_COMMON_TEXTURE_MAP_MODE_BUFFER)) {
|
||||
// Now that data has been written into the buffer,
|
||||
// we need to copy its contents into the image
|
||||
VkImageAspectFlags aspectMask = imageFormatInfo(pResource->GetPackedFormat())->aspectMask;
|
||||
VkImageSubresource subresource = pResource->GetSubresourceFromIndex(aspectMask, Subresource);
|
||||
if ((mapType != D3D11_MAP_READ) && (pResource->GetMapMode() == D3D11_COMMON_TEXTURE_MAP_MODE_BUFFER)) {
|
||||
if (pResource->NeedsDirtyRegionTracking()) {
|
||||
for (uint32_t i = 0; i < pResource->GetDirtyRegionCount(Subresource); i++) {
|
||||
D3D11_COMMON_TEXTURE_REGION region = pResource->GetDirtyRegion(Subresource, i);
|
||||
UpdateDirtyImageRegion(pResource, Subresource, ®ion);
|
||||
}
|
||||
|
||||
UpdateImage(pResource, &subresource, VkOffset3D { 0, 0, 0 },
|
||||
pResource->MipLevelExtent(subresource.mipLevel),
|
||||
DxvkBufferSlice(pResource->GetMappedBuffer(Subresource)));
|
||||
pResource->ClearDirtyRegions(Subresource);
|
||||
} else {
|
||||
UpdateDirtyImageRegion(pResource, Subresource, nullptr);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void D3D11ImmediateContext::ReadbackImageBuffer(
|
||||
D3D11CommonTexture* pResource,
|
||||
UINT Subresource) {
|
||||
VkImageAspectFlags aspectMask = lookupFormatInfo(pResource->GetPackedFormat())->aspectMask;
|
||||
VkImageSubresource subresource = pResource->GetSubresourceFromIndex(aspectMask, Subresource);
|
||||
|
||||
EmitCs([
|
||||
cSrcImage = pResource->GetImage(),
|
||||
cSrcSubresource = vk::makeSubresourceLayers(subresource),
|
||||
cDstBuffer = pResource->GetMappedBuffer(Subresource),
|
||||
cPackedFormat = pResource->GetPackedFormat()
|
||||
] (DxvkContext* ctx) {
|
||||
VkOffset3D offset = { 0, 0, 0 };
|
||||
VkExtent3D extent = cSrcImage->mipLevelExtent(cSrcSubresource.mipLevel);
|
||||
|
||||
if (cSrcSubresource.aspectMask != (VK_IMAGE_ASPECT_DEPTH_BIT | VK_IMAGE_ASPECT_STENCIL_BIT)) {
|
||||
ctx->copyImageToBuffer(cDstBuffer, 0, 0, 0,
|
||||
cSrcImage, cSrcSubresource, offset, extent);
|
||||
} else {
|
||||
ctx->copyDepthStencilImageToPackedBuffer(cDstBuffer, 0,
|
||||
VkOffset2D { 0, 0 },
|
||||
VkExtent2D { extent.width, extent.height },
|
||||
cSrcImage, cSrcSubresource,
|
||||
VkOffset2D { 0, 0 },
|
||||
VkExtent2D { extent.width, extent.height },
|
||||
cPackedFormat);
|
||||
}
|
||||
});
|
||||
|
||||
if (pResource->HasSequenceNumber())
|
||||
TrackTextureSequenceNumber(pResource, Subresource);
|
||||
}
|
||||
|
||||
|
||||
void D3D11ImmediateContext::UpdateDirtyImageRegion(
|
||||
D3D11CommonTexture* pResource,
|
||||
UINT Subresource,
|
||||
const D3D11_COMMON_TEXTURE_REGION* pRegion) {
|
||||
auto formatInfo = lookupFormatInfo(pResource->GetPackedFormat());
|
||||
auto subresource = vk::makeSubresourceLayers(
|
||||
pResource->GetSubresourceFromIndex(formatInfo->aspectMask, Subresource));
|
||||
|
||||
// Update the entire image if no dirty region was specified
|
||||
D3D11_COMMON_TEXTURE_REGION region;
|
||||
|
||||
if (pRegion) {
|
||||
region = *pRegion;
|
||||
} else {
|
||||
region.Offset = VkOffset3D { 0, 0, 0 };
|
||||
region.Extent = pResource->MipLevelExtent(subresource.mipLevel);
|
||||
}
|
||||
|
||||
auto subresourceLayout = pResource->GetSubresourceLayout(formatInfo->aspectMask, Subresource);
|
||||
|
||||
// Update dirty region one aspect at a time, due to
|
||||
// how the data is laid out in the staging buffer.
|
||||
for (uint32_t i = 0; i < pResource->GetPlaneCount(); i++) {
|
||||
subresource.aspectMask = formatInfo->aspectMask;
|
||||
|
||||
if (formatInfo->flags.test(DxvkFormatFlag::MultiPlane))
|
||||
subresource.aspectMask = vk::getPlaneAspect(i);
|
||||
|
||||
EmitCs([
|
||||
cDstImage = pResource->GetImage(),
|
||||
cDstSubresource = subresource,
|
||||
cDstOffset = region.Offset,
|
||||
cDstExtent = region.Extent,
|
||||
cSrcBuffer = pResource->GetMappedBuffer(Subresource),
|
||||
cSrcOffset = pResource->ComputeMappedOffset(Subresource, i, region.Offset),
|
||||
cSrcRowPitch = subresourceLayout.RowPitch,
|
||||
cSrcDepthPitch = subresourceLayout.DepthPitch,
|
||||
cPackedFormat = pResource->GetPackedFormat()
|
||||
] (DxvkContext* ctx) {
|
||||
if (cDstSubresource.aspectMask != (VK_IMAGE_ASPECT_DEPTH_BIT | VK_IMAGE_ASPECT_STENCIL_BIT)) {
|
||||
ctx->copyBufferToImage(
|
||||
cDstImage, cDstSubresource, cDstOffset, cDstExtent,
|
||||
cSrcBuffer, cSrcOffset, cSrcRowPitch, cSrcDepthPitch);
|
||||
} else {
|
||||
ctx->copyPackedBufferToDepthStencilImage(
|
||||
cDstImage, cDstSubresource,
|
||||
VkOffset2D { cDstOffset.x, cDstOffset.y },
|
||||
VkExtent2D { cDstExtent.width, cDstExtent.height },
|
||||
cSrcBuffer, 0,
|
||||
VkOffset2D { cDstOffset.x, cDstOffset.y },
|
||||
VkExtent2D { cDstExtent.width, cDstExtent.height },
|
||||
cPackedFormat);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
if (pResource->HasSequenceNumber())
|
||||
TrackTextureSequenceNumber(pResource, Subresource);
|
||||
}
|
||||
|
||||
|
||||
void D3D11ImmediateContext::UpdateMappedBuffer(
|
||||
D3D11Buffer* pDstBuffer,
|
||||
UINT Offset,
|
||||
@ -646,9 +730,12 @@ namespace dxvk {
|
||||
|
||||
if (!pState)
|
||||
return;
|
||||
|
||||
Com<D3D11DeviceContextState> oldState = std::move(m_stateObject);
|
||||
Com<D3D11DeviceContextState> newState = static_cast<D3D11DeviceContextState*>(pState);
|
||||
|
||||
// Reset all state affected by the current context state
|
||||
ResetCommandListState();
|
||||
|
||||
Com<D3D11DeviceContextState, false> oldState = std::move(m_stateObject);
|
||||
Com<D3D11DeviceContextState, false> newState = static_cast<D3D11DeviceContextState*>(pState);
|
||||
|
||||
if (oldState == nullptr)
|
||||
oldState = new D3D11DeviceContextState(m_parent);
|
||||
@ -661,7 +748,76 @@ namespace dxvk {
|
||||
oldState->SetState(m_state);
|
||||
newState->GetState(m_state);
|
||||
|
||||
RestoreState();
|
||||
// Restore all state affected by the new context state
|
||||
RestoreCommandListState();
|
||||
}
|
||||
|
||||
|
||||
void D3D11ImmediateContext::Acquire11on12Resource(
|
||||
ID3D11Resource* pResource,
|
||||
VkImageLayout SrcLayout) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
auto texture = GetCommonTexture(pResource);
|
||||
auto buffer = GetCommonBuffer(pResource);
|
||||
|
||||
if (buffer) {
|
||||
EmitCs([
|
||||
cBuffer = buffer->GetBuffer()
|
||||
] (DxvkContext* ctx) {
|
||||
ctx->emitBufferBarrier(cBuffer,
|
||||
VK_PIPELINE_STAGE_ALL_COMMANDS_BIT,
|
||||
VK_ACCESS_MEMORY_WRITE_BIT | VK_ACCESS_MEMORY_READ_BIT,
|
||||
cBuffer->info().stages,
|
||||
cBuffer->info().access);
|
||||
});
|
||||
} else if (texture) {
|
||||
EmitCs([
|
||||
cImage = texture->GetImage(),
|
||||
cLayout = SrcLayout
|
||||
] (DxvkContext* ctx) {
|
||||
ctx->emitImageBarrier(cImage, cLayout,
|
||||
VK_PIPELINE_STAGE_ALL_COMMANDS_BIT,
|
||||
VK_ACCESS_MEMORY_WRITE_BIT | VK_ACCESS_MEMORY_READ_BIT,
|
||||
cImage->info().layout,
|
||||
cImage->info().stages,
|
||||
cImage->info().access);
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void D3D11ImmediateContext::Release11on12Resource(
|
||||
ID3D11Resource* pResource,
|
||||
VkImageLayout DstLayout) {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
auto texture = GetCommonTexture(pResource);
|
||||
auto buffer = GetCommonBuffer(pResource);
|
||||
|
||||
if (buffer) {
|
||||
EmitCs([
|
||||
cBuffer = buffer->GetBuffer()
|
||||
] (DxvkContext* ctx) {
|
||||
ctx->emitBufferBarrier(cBuffer,
|
||||
cBuffer->info().stages,
|
||||
cBuffer->info().access,
|
||||
VK_PIPELINE_STAGE_ALL_COMMANDS_BIT,
|
||||
VK_ACCESS_MEMORY_WRITE_BIT | VK_ACCESS_MEMORY_READ_BIT);
|
||||
});
|
||||
} else if (texture) {
|
||||
EmitCs([
|
||||
cImage = texture->GetImage(),
|
||||
cLayout = DstLayout
|
||||
] (DxvkContext* ctx) {
|
||||
ctx->emitImageBarrier(cImage,
|
||||
cImage->info().layout,
|
||||
cImage->info().stages,
|
||||
cImage->info().access,
|
||||
cLayout, VK_PIPELINE_STAGE_ALL_COMMANDS_BIT,
|
||||
VK_ACCESS_MEMORY_WRITE_BIT | VK_ACCESS_MEMORY_READ_BIT);
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -682,6 +838,15 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
void D3D11ImmediateContext::EndFrame() {
|
||||
D3D10DeviceLock lock = LockContext();
|
||||
|
||||
EmitCs<false>([] (DxvkContext* ctx) {
|
||||
ctx->endFrame();
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
bool D3D11ImmediateContext::WaitForResource(
|
||||
const Rc<DxvkResource>& Resource,
|
||||
uint64_t SequenceNumber,
|
||||
@ -707,14 +872,14 @@ namespace dxvk {
|
||||
// We don't have to wait, but misbehaving games may
|
||||
// still try to spin on `Map` until the resource is
|
||||
// idle, so we should flush pending commands
|
||||
FlushImplicit(FALSE);
|
||||
ConsiderFlush(GpuFlushType::ImplicitSynchronization);
|
||||
return false;
|
||||
}
|
||||
} else {
|
||||
if (isInUse) {
|
||||
// Make sure pending commands using the resource get
|
||||
// executed on the the GPU if we have to wait for it
|
||||
Flush();
|
||||
ExecuteFlush(GpuFlushType::ImplicitSynchronization, nullptr, false);
|
||||
SynchronizeCsThread(SequenceNumber);
|
||||
|
||||
m_device->waitForResource(Resource, access);
|
||||
@ -727,7 +892,6 @@ namespace dxvk {
|
||||
|
||||
void D3D11ImmediateContext::EmitCsChunk(DxvkCsChunkRef&& chunk) {
|
||||
m_csSeqNum = m_csThread.dispatchChunk(std::move(chunk));
|
||||
m_csIsBusy = true;
|
||||
}
|
||||
|
||||
|
||||
@ -737,7 +901,7 @@ namespace dxvk {
|
||||
uint64_t sequenceNumber = GetCurrentSequenceNumber();
|
||||
pResource->TrackSequenceNumber(Subresource, sequenceNumber);
|
||||
|
||||
FlushImplicit(TRUE);
|
||||
ConsiderFlush(GpuFlushType::ImplicitStrongHint);
|
||||
}
|
||||
|
||||
|
||||
@ -746,7 +910,7 @@ namespace dxvk {
|
||||
uint64_t sequenceNumber = GetCurrentSequenceNumber();
|
||||
pResource->TrackSequenceNumber(sequenceNumber);
|
||||
|
||||
FlushImplicit(TRUE);
|
||||
ConsiderFlush(GpuFlushType::ImplicitStrongHint);
|
||||
}
|
||||
|
||||
|
||||
@ -758,40 +922,67 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
void D3D11ImmediateContext::FlushImplicit(BOOL StrongHint) {
|
||||
// Flush only if the GPU is about to go idle, in
|
||||
// order to keep the number of submissions low.
|
||||
uint32_t pending = m_device->pendingSubmissions();
|
||||
|
||||
if (StrongHint || pending <= MaxPendingSubmits) {
|
||||
auto now = dxvk::high_resolution_clock::now();
|
||||
|
||||
uint32_t delay = MinFlushIntervalUs
|
||||
+ IncFlushIntervalUs * pending;
|
||||
|
||||
// Prevent flushing too often in short intervals.
|
||||
if (now - m_lastFlush >= std::chrono::microseconds(delay))
|
||||
Flush();
|
||||
}
|
||||
uint64_t D3D11ImmediateContext::GetPendingCsChunks() {
|
||||
return GetCurrentSequenceNumber() - m_flushSeqNum;
|
||||
}
|
||||
|
||||
|
||||
void D3D11ImmediateContext::SignalEvent(HANDLE hEvent) {
|
||||
uint64_t value = ++m_eventCount;
|
||||
void D3D11ImmediateContext::ConsiderFlush(
|
||||
GpuFlushType FlushType) {
|
||||
uint64_t chunkId = GetCurrentSequenceNumber();
|
||||
uint64_t submissionId = m_submissionFence->value();
|
||||
|
||||
if (m_eventSignal == nullptr)
|
||||
m_eventSignal = new sync::CallbackFence();
|
||||
if (m_flushTracker.considerFlush(FlushType, chunkId, submissionId))
|
||||
ExecuteFlush(FlushType, nullptr, false);
|
||||
}
|
||||
|
||||
m_eventSignal->setCallback(value, [hEvent] {
|
||||
SetEvent(hEvent);
|
||||
});
|
||||
|
||||
EmitCs([
|
||||
cSignal = m_eventSignal,
|
||||
cValue = value
|
||||
void D3D11ImmediateContext::ExecuteFlush(
|
||||
GpuFlushType FlushType,
|
||||
HANDLE hEvent,
|
||||
BOOL Synchronize) {
|
||||
bool synchronizeSubmission = Synchronize && m_parent->Is11on12Device();
|
||||
|
||||
if (synchronizeSubmission)
|
||||
m_submitStatus.result = VK_NOT_READY;
|
||||
|
||||
// Flush init context so that new resources are fully initialized
|
||||
// before the app can access them in any way. This has to happen
|
||||
// unconditionally since we may otherwise deadlock on Map.
|
||||
m_parent->FlushInitContext();
|
||||
|
||||
// Exit early if there's nothing to do
|
||||
if (!GetPendingCsChunks() && !hEvent)
|
||||
return;
|
||||
|
||||
// Signal the submission fence and flush the command list
|
||||
uint64_t submissionId = ++m_submissionId;
|
||||
|
||||
if (hEvent) {
|
||||
m_submissionFence->setCallback(submissionId, [hEvent] {
|
||||
SetEvent(hEvent);
|
||||
});
|
||||
}
|
||||
|
||||
EmitCs<false>([
|
||||
cSubmissionFence = m_submissionFence,
|
||||
cSubmissionId = submissionId,
|
||||
cSubmissionStatus = synchronizeSubmission ? &m_submitStatus : nullptr
|
||||
] (DxvkContext* ctx) {
|
||||
ctx->signal(cSignal, cValue);
|
||||
ctx->signal(cSubmissionFence, cSubmissionId);
|
||||
ctx->flushCommandList(cSubmissionStatus);
|
||||
});
|
||||
|
||||
FlushCsChunk();
|
||||
|
||||
// Notify flush tracker about the flush
|
||||
m_flushSeqNum = m_csSeqNum;
|
||||
m_flushTracker.notifyFlush(m_flushSeqNum, submissionId);
|
||||
|
||||
// If necessary, block calling thread until the
|
||||
// Vulkan queue submission is performed.
|
||||
if (synchronizeSubmission)
|
||||
m_device->waitForSubmission(&m_submitStatus);
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -12,11 +12,12 @@ namespace dxvk {
|
||||
|
||||
class D3D11Buffer;
|
||||
class D3D11CommonTexture;
|
||||
|
||||
class D3D11ImmediateContext : public D3D11DeviceContext {
|
||||
|
||||
class D3D11ImmediateContext : public D3D11CommonContext<D3D11ImmediateContext> {
|
||||
friend class D3D11CommonContext<D3D11ImmediateContext>;
|
||||
friend class D3D11SwapChain;
|
||||
friend class D3D11VideoContext;
|
||||
friend class D3D11DeviceContext;
|
||||
friend class D3D11DXGIKeyedMutex;
|
||||
public:
|
||||
|
||||
D3D11ImmediateContext(
|
||||
@ -28,10 +29,6 @@ namespace dxvk {
|
||||
REFIID riid,
|
||||
void** ppvObject);
|
||||
|
||||
D3D11_DEVICE_CONTEXT_TYPE STDMETHODCALLTYPE GetType();
|
||||
|
||||
UINT STDMETHODCALLTYPE GetContextFlags();
|
||||
|
||||
HRESULT STDMETHODCALLTYPE GetData(
|
||||
ID3D11Asynchronous* pAsync,
|
||||
void* pData,
|
||||
@ -77,61 +74,45 @@ namespace dxvk {
|
||||
ID3D11Resource* pResource,
|
||||
UINT Subresource);
|
||||
|
||||
void STDMETHODCALLTYPE UpdateSubresource(
|
||||
ID3D11Resource* pDstResource,
|
||||
UINT DstSubresource,
|
||||
const D3D11_BOX* pDstBox,
|
||||
const void* pSrcData,
|
||||
UINT SrcRowPitch,
|
||||
UINT SrcDepthPitch);
|
||||
|
||||
void STDMETHODCALLTYPE UpdateSubresource1(
|
||||
ID3D11Resource* pDstResource,
|
||||
UINT DstSubresource,
|
||||
const D3D11_BOX* pDstBox,
|
||||
const void* pSrcData,
|
||||
UINT SrcRowPitch,
|
||||
UINT SrcDepthPitch,
|
||||
UINT CopyFlags);
|
||||
|
||||
void STDMETHODCALLTYPE OMSetRenderTargets(
|
||||
UINT NumViews,
|
||||
ID3D11RenderTargetView* const* ppRenderTargetViews,
|
||||
ID3D11DepthStencilView* pDepthStencilView);
|
||||
|
||||
void STDMETHODCALLTYPE OMSetRenderTargetsAndUnorderedAccessViews(
|
||||
UINT NumRTVs,
|
||||
ID3D11RenderTargetView* const* ppRenderTargetViews,
|
||||
ID3D11DepthStencilView* pDepthStencilView,
|
||||
UINT UAVStartSlot,
|
||||
UINT NumUAVs,
|
||||
ID3D11UnorderedAccessView* const* ppUnorderedAccessViews,
|
||||
const UINT* pUAVInitialCounts);
|
||||
|
||||
void STDMETHODCALLTYPE SwapDeviceContextState(
|
||||
ID3DDeviceContextState* pState,
|
||||
ID3DDeviceContextState** ppPreviousState);
|
||||
|
||||
void Acquire11on12Resource(
|
||||
ID3D11Resource* pResource,
|
||||
VkImageLayout SrcLayout);
|
||||
|
||||
void Release11on12Resource(
|
||||
ID3D11Resource* pResource,
|
||||
VkImageLayout DstLayout);
|
||||
|
||||
void SynchronizeCsThread(
|
||||
uint64_t SequenceNumber);
|
||||
|
||||
|
||||
D3D10DeviceLock LockContext() {
|
||||
return m_multithread.AcquireLock();
|
||||
}
|
||||
|
||||
private:
|
||||
|
||||
DxvkCsThread m_csThread;
|
||||
uint64_t m_csSeqNum = 0ull;
|
||||
bool m_csIsBusy = false;
|
||||
|
||||
Rc<sync::CallbackFence> m_eventSignal;
|
||||
uint64_t m_eventCount = 0ull;
|
||||
uint32_t m_mappedImageCount = 0u;
|
||||
|
||||
VkDeviceSize m_maxImplicitDiscardSize = 0ull;
|
||||
|
||||
dxvk::high_resolution_clock::time_point m_lastFlush
|
||||
= dxvk::high_resolution_clock::now();
|
||||
|
||||
D3D11VideoContext m_videoContext;
|
||||
Com<D3D11DeviceContextState> m_stateObject;
|
||||
Rc<sync::CallbackFence> m_submissionFence;
|
||||
uint64_t m_submissionId = 0ull;
|
||||
DxvkSubmitStatus m_submitStatus;
|
||||
|
||||
uint64_t m_flushSeqNum = 0ull;
|
||||
GpuFlushTracker m_flushTracker;
|
||||
|
||||
D3D10Multithread m_multithread;
|
||||
D3D11VideoContext m_videoContext;
|
||||
|
||||
Com<D3D11DeviceContextState, false> m_stateObject;
|
||||
|
||||
HRESULT MapBuffer(
|
||||
D3D11Buffer* pResource,
|
||||
@ -150,20 +131,31 @@ namespace dxvk {
|
||||
D3D11CommonTexture* pResource,
|
||||
UINT Subresource);
|
||||
|
||||
void ReadbackImageBuffer(
|
||||
D3D11CommonTexture* pResource,
|
||||
UINT Subresource);
|
||||
|
||||
void UpdateDirtyImageRegion(
|
||||
D3D11CommonTexture* pResource,
|
||||
UINT Subresource,
|
||||
const D3D11_COMMON_TEXTURE_REGION* pRegion);
|
||||
|
||||
void UpdateMappedBuffer(
|
||||
D3D11Buffer* pDstBuffer,
|
||||
UINT Offset,
|
||||
UINT Length,
|
||||
const void* pSrcData,
|
||||
UINT CopyFlags);
|
||||
D3D11Buffer* pDstBuffer,
|
||||
UINT Offset,
|
||||
UINT Length,
|
||||
const void* pSrcData,
|
||||
UINT CopyFlags);
|
||||
|
||||
void SynchronizeDevice();
|
||||
|
||||
void EndFrame();
|
||||
|
||||
bool WaitForResource(
|
||||
const Rc<DxvkResource>& Resource,
|
||||
uint64_t SequenceNumber,
|
||||
D3D11_MAP MapType,
|
||||
UINT MapFlags);
|
||||
const Rc<DxvkResource>& Resource,
|
||||
uint64_t SequenceNumber,
|
||||
D3D11_MAP MapType,
|
||||
UINT MapFlags);
|
||||
|
||||
void EmitCsChunk(DxvkCsChunkRef&& chunk);
|
||||
|
||||
@ -176,10 +168,16 @@ namespace dxvk {
|
||||
|
||||
uint64_t GetCurrentSequenceNumber();
|
||||
|
||||
void FlushImplicit(BOOL StrongHint);
|
||||
uint64_t GetPendingCsChunks();
|
||||
|
||||
void ConsiderFlush(
|
||||
GpuFlushType FlushType);
|
||||
|
||||
void ExecuteFlush(
|
||||
GpuFlushType FlushType,
|
||||
HANDLE hEvent,
|
||||
BOOL Synchronize);
|
||||
|
||||
void SignalEvent(HANDLE hEvent);
|
||||
|
||||
};
|
||||
|
||||
}
|
||||
|
@ -15,128 +15,237 @@
|
||||
|
||||
namespace dxvk {
|
||||
|
||||
/**
|
||||
* \brief Per-stage state
|
||||
*
|
||||
* Stores an object of the given type for each shader stage.
|
||||
* \tparam Object type
|
||||
*/
|
||||
template<typename T>
|
||||
class D3D11ShaderStageState {
|
||||
|
||||
public:
|
||||
|
||||
T& operator [] (DxbcProgramType type) { return m_state[uint32_t(type)]; }
|
||||
const T& operator [] (DxbcProgramType type) const { return m_state[uint32_t(type)]; }
|
||||
|
||||
/**
|
||||
* \brief Calls reset method on all objects
|
||||
*/
|
||||
void reset() {
|
||||
for (auto& state : m_state)
|
||||
state.reset();
|
||||
}
|
||||
|
||||
private:
|
||||
|
||||
std::array<T, 6> m_state = { };
|
||||
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* \brief Constant buffer bindings
|
||||
*
|
||||
* Stores the bound buffer range from a runtime point of view,
|
||||
* as well as the range that is actually bound to the context.
|
||||
*/
|
||||
struct D3D11ConstantBufferBinding {
|
||||
Com<D3D11Buffer> buffer = nullptr;
|
||||
Com<D3D11Buffer, false> buffer = nullptr;
|
||||
UINT constantOffset = 0;
|
||||
UINT constantCount = 0;
|
||||
UINT constantBound = 0;
|
||||
};
|
||||
|
||||
using D3D11ConstantBufferBindings = std::array<
|
||||
D3D11ConstantBufferBinding, D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT>;
|
||||
|
||||
|
||||
using D3D11SamplerBindings = std::array<
|
||||
D3D11SamplerState*, D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT>;
|
||||
|
||||
|
||||
struct D3D11ShaderResourceBindings {
|
||||
std::array<Com<D3D11ShaderResourceView>, D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT> views = { };
|
||||
DxvkBindingSet<D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT> hazardous = { };
|
||||
};
|
||||
|
||||
|
||||
using D3D11UnorderedAccessBindings = std::array<
|
||||
Com<D3D11UnorderedAccessView>, D3D11_1_UAV_SLOT_COUNT>;
|
||||
|
||||
|
||||
struct D3D11ContextStateVS {
|
||||
Com<D3D11VertexShader> shader = nullptr;
|
||||
D3D11ConstantBufferBindings constantBuffers = { };
|
||||
D3D11SamplerBindings samplers = { };
|
||||
D3D11ShaderResourceBindings shaderResources = { };
|
||||
};
|
||||
|
||||
|
||||
struct D3D11ContextStateHS {
|
||||
Com<D3D11HullShader> shader = nullptr;
|
||||
D3D11ConstantBufferBindings constantBuffers = { };
|
||||
D3D11SamplerBindings samplers = { };
|
||||
D3D11ShaderResourceBindings shaderResources = { };
|
||||
};
|
||||
|
||||
|
||||
struct D3D11ContextStateDS {
|
||||
Com<D3D11DomainShader> shader = nullptr;
|
||||
D3D11ConstantBufferBindings constantBuffers = { };
|
||||
D3D11SamplerBindings samplers = { };
|
||||
D3D11ShaderResourceBindings shaderResources = { };
|
||||
};
|
||||
|
||||
|
||||
struct D3D11ContextStateGS {
|
||||
Com<D3D11GeometryShader> shader = nullptr;
|
||||
D3D11ConstantBufferBindings constantBuffers = { };
|
||||
D3D11SamplerBindings samplers = { };
|
||||
D3D11ShaderResourceBindings shaderResources = { };
|
||||
};
|
||||
|
||||
|
||||
struct D3D11ContextStatePS {
|
||||
Com<D3D11PixelShader> shader = nullptr;
|
||||
D3D11ConstantBufferBindings constantBuffers = { };
|
||||
D3D11SamplerBindings samplers = { };
|
||||
D3D11ShaderResourceBindings shaderResources = { };
|
||||
D3D11UnorderedAccessBindings unorderedAccessViews = { };
|
||||
};
|
||||
|
||||
|
||||
struct D3D11ContextStateCS {
|
||||
Com<D3D11ComputeShader> shader = nullptr;
|
||||
D3D11ConstantBufferBindings constantBuffers = { };
|
||||
D3D11SamplerBindings samplers = { };
|
||||
D3D11ShaderResourceBindings shaderResources = { };
|
||||
D3D11UnorderedAccessBindings unorderedAccessViews = { };
|
||||
struct D3D11ShaderStageCbvBinding {
|
||||
std::array<D3D11ConstantBufferBinding, D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT> buffers = { };
|
||||
|
||||
DxvkBindingSet<D3D11_1_UAV_SLOT_COUNT> uavMask = { };
|
||||
uint32_t maxCount = 0;
|
||||
|
||||
void reset() {
|
||||
for (uint32_t i = 0; i < maxCount; i++)
|
||||
buffers[i] = D3D11ConstantBufferBinding();
|
||||
|
||||
maxCount = 0;
|
||||
}
|
||||
};
|
||||
|
||||
using D3D11CbvBindings = D3D11ShaderStageState<D3D11ShaderStageCbvBinding>;
|
||||
|
||||
/**
|
||||
* \brief Shader resource bindings
|
||||
*
|
||||
* Stores bound shader resource views, as well as a bit
|
||||
* set of views that are potentially hazardous.
|
||||
*/
|
||||
struct D3D11ShaderStageSrvBinding {
|
||||
std::array<Com<D3D11ShaderResourceView, false>, D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT> views = { };
|
||||
DxvkBindingSet<D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT> hazardous = { };
|
||||
|
||||
uint32_t maxCount = 0;
|
||||
|
||||
void reset() {
|
||||
for (uint32_t i = 0; i < maxCount; i++)
|
||||
views[i] = nullptr;
|
||||
|
||||
hazardous.clear();
|
||||
maxCount = 0;
|
||||
}
|
||||
};
|
||||
|
||||
using D3D11SrvBindings = D3D11ShaderStageState<D3D11ShaderStageSrvBinding>;
|
||||
|
||||
/**
|
||||
* \brief Sampler bindings
|
||||
*
|
||||
* Stores bound samplers.
|
||||
*/
|
||||
struct D3D11ShaderStageSamplerBinding {
|
||||
std::array<D3D11SamplerState*, D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT> samplers = { };
|
||||
|
||||
uint32_t maxCount = 0;
|
||||
|
||||
void reset() {
|
||||
for (uint32_t i = 0; i < maxCount; i++)
|
||||
samplers[i] = nullptr;
|
||||
|
||||
maxCount = 0;
|
||||
}
|
||||
};
|
||||
|
||||
using D3D11SamplerBindings = D3D11ShaderStageState<D3D11ShaderStageSamplerBinding>;
|
||||
|
||||
/**
|
||||
* \brief UAV bindings
|
||||
*
|
||||
* Stores bound UAVs. For compute shader UAVs,
|
||||
* we also store a bit mask of bound UAVs.
|
||||
*/
|
||||
using D3D11ShaderStageUavBinding = std::array<Com<D3D11UnorderedAccessView, false>, D3D11_1_UAV_SLOT_COUNT>;
|
||||
|
||||
struct D3D11UavBindings {
|
||||
D3D11ShaderStageUavBinding views = { };
|
||||
DxvkBindingSet<D3D11_1_UAV_SLOT_COUNT> mask = { };
|
||||
|
||||
uint32_t maxCount = 0;
|
||||
|
||||
void reset() {
|
||||
for (uint32_t i = 0; i < maxCount; i++)
|
||||
views[i] = nullptr;
|
||||
|
||||
mask.clear();
|
||||
maxCount = 0;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* \brief Input assembly state
|
||||
*
|
||||
* Stores vertex buffers, the index buffer, the
|
||||
* input layout, and the dynamic primitive topology.
|
||||
*/
|
||||
struct D3D11VertexBufferBinding {
|
||||
Com<D3D11Buffer> buffer = nullptr;
|
||||
UINT offset = 0;
|
||||
UINT stride = 0;
|
||||
Com<D3D11Buffer, false> buffer = nullptr;
|
||||
UINT offset = 0;
|
||||
UINT stride = 0;
|
||||
};
|
||||
|
||||
|
||||
struct D3D11IndexBufferBinding {
|
||||
Com<D3D11Buffer> buffer = nullptr;
|
||||
UINT offset = 0;
|
||||
DXGI_FORMAT format = DXGI_FORMAT_UNKNOWN;
|
||||
Com<D3D11Buffer, false> buffer = nullptr;
|
||||
UINT offset = 0;
|
||||
DXGI_FORMAT format = DXGI_FORMAT_UNKNOWN;
|
||||
};
|
||||
|
||||
|
||||
struct D3D11ContextStateID {
|
||||
Com<D3D11Buffer> argBuffer = nullptr;
|
||||
Com<D3D11Buffer> cntBuffer = nullptr;
|
||||
};
|
||||
|
||||
|
||||
struct D3D11ContextStateIA {
|
||||
Com<D3D11InputLayout> inputLayout = nullptr;
|
||||
D3D11_PRIMITIVE_TOPOLOGY primitiveTopology = D3D11_PRIMITIVE_TOPOLOGY_UNDEFINED;
|
||||
Com<D3D11InputLayout, false> inputLayout = nullptr;
|
||||
D3D11_PRIMITIVE_TOPOLOGY primitiveTopology = D3D11_PRIMITIVE_TOPOLOGY_UNDEFINED;
|
||||
|
||||
std::array<D3D11VertexBufferBinding, D3D11_IA_VERTEX_INPUT_RESOURCE_SLOT_COUNT> vertexBuffers = { };
|
||||
D3D11IndexBufferBinding indexBuffer = { };
|
||||
|
||||
uint32_t maxVbCount = 0;
|
||||
|
||||
void reset() {
|
||||
inputLayout = nullptr;
|
||||
|
||||
primitiveTopology = D3D11_PRIMITIVE_TOPOLOGY_UNDEFINED;
|
||||
|
||||
for (uint32_t i = 0; i < maxVbCount; i++)
|
||||
vertexBuffers[i] = D3D11VertexBufferBinding();
|
||||
|
||||
indexBuffer = D3D11IndexBufferBinding();
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* \brief Output merger state
|
||||
*
|
||||
* Stores RTV, DSV, and graphics UAV bindings, as well as related state.
|
||||
*/
|
||||
using D3D11RenderTargetViewBinding = std::array<Com<D3D11RenderTargetView, false>, D3D11_SIMULTANEOUS_RENDER_TARGET_COUNT>;
|
||||
|
||||
struct D3D11ContextStateOM {
|
||||
std::array<Com<D3D11RenderTargetView, false>, D3D11_SIMULTANEOUS_RENDER_TARGET_COUNT> renderTargetViews = { };
|
||||
Com<D3D11DepthStencilView, false> depthStencilView = { };
|
||||
D3D11ShaderStageUavBinding uavs = { };
|
||||
D3D11RenderTargetViewBinding rtvs = { };
|
||||
Com<D3D11DepthStencilView, false> dsv = { };
|
||||
|
||||
D3D11BlendState* cbState = nullptr;
|
||||
D3D11DepthStencilState* dsState = nullptr;
|
||||
|
||||
FLOAT blendFactor[4] = { 1.0f, 1.0f, 1.0f, 1.0f };
|
||||
UINT sampleMask = 0xFFFFFFFFu;
|
||||
UINT stencilRef = 0u;
|
||||
|
||||
UINT sampleCount = 0u;
|
||||
UINT sampleMask = D3D11_DEFAULT_SAMPLE_MASK;
|
||||
UINT stencilRef = D3D11_DEFAULT_STENCIL_REFERENCE;
|
||||
|
||||
UINT maxRtv = 0u;
|
||||
UINT maxUav = 0u;
|
||||
|
||||
void reset() {
|
||||
for (uint32_t i = 0; i < maxUav; i++)
|
||||
uavs[i] = nullptr;
|
||||
|
||||
for (uint32_t i = 0; i < maxRtv; i++)
|
||||
rtvs[i] = nullptr;
|
||||
|
||||
dsv = nullptr;
|
||||
|
||||
cbState = nullptr;
|
||||
dsState = nullptr;
|
||||
|
||||
for (uint32_t i = 0; i < 4; i++)
|
||||
blendFactor[i] = 1.0f;
|
||||
|
||||
sampleCount = 0u;
|
||||
sampleMask = D3D11_DEFAULT_SAMPLE_MASK;
|
||||
stencilRef = D3D11_DEFAULT_STENCIL_REFERENCE;
|
||||
|
||||
maxRtv = 0;
|
||||
maxUav = 0;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* \brief Indirect draw state
|
||||
*
|
||||
* Stores the current indirct draw
|
||||
* argument and draw count buffer.
|
||||
*/
|
||||
struct D3D11ContextStateID {
|
||||
Com<D3D11Buffer, false> argBuffer = nullptr;
|
||||
Com<D3D11Buffer, false> cntBuffer = nullptr;
|
||||
|
||||
void reset() {
|
||||
argBuffer = nullptr;
|
||||
cntBuffer = nullptr;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* \brief Rasterizer state
|
||||
*
|
||||
* Stores viewport info and the rasterizer state object.
|
||||
*/
|
||||
struct D3D11ContextStateRS {
|
||||
uint32_t numViewports = 0;
|
||||
uint32_t numScissors = 0;
|
||||
@ -145,43 +254,97 @@ namespace dxvk {
|
||||
std::array<D3D11_RECT, D3D11_VIEWPORT_AND_SCISSORRECT_OBJECT_COUNT_PER_PIPELINE> scissors = { };
|
||||
|
||||
D3D11RasterizerState* state = nullptr;
|
||||
|
||||
void reset() {
|
||||
for (uint32_t i = 0; i < numViewports; i++)
|
||||
viewports[i] = D3D11_VIEWPORT();
|
||||
|
||||
for (uint32_t i = 0; i < numScissors; i++)
|
||||
scissors[i] = D3D11_RECT();
|
||||
|
||||
numViewports = 0;
|
||||
numScissors = 0;
|
||||
|
||||
state = nullptr;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* \brief Stream output binding
|
||||
*
|
||||
* Stores stream output buffers with offset.
|
||||
*/
|
||||
struct D3D11ContextSoTarget {
|
||||
Com<D3D11Buffer> buffer = nullptr;
|
||||
UINT offset = 0;
|
||||
Com<D3D11Buffer, false> buffer = nullptr;
|
||||
UINT offset = 0;
|
||||
};
|
||||
|
||||
|
||||
struct D3D11ContextStateSO {
|
||||
std::array<D3D11ContextSoTarget, D3D11_SO_BUFFER_SLOT_COUNT> targets = { };
|
||||
|
||||
void reset() {
|
||||
for (uint32_t i = 0; i < targets.size(); i++)
|
||||
targets[i] = D3D11ContextSoTarget();
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* \brief Predication state
|
||||
*
|
||||
* Stores predication info.
|
||||
*/
|
||||
struct D3D11ContextStatePR {
|
||||
Com<D3D11Query> predicateObject = nullptr;
|
||||
BOOL predicateValue = FALSE;
|
||||
Com<D3D11Query, false> predicateObject = nullptr;
|
||||
BOOL predicateValue = false;
|
||||
|
||||
void reset() {
|
||||
predicateObject = nullptr;
|
||||
predicateValue = false;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* \brief Context state
|
||||
*/
|
||||
struct D3D11ContextState {
|
||||
D3D11ContextStateCS cs;
|
||||
D3D11ContextStateDS ds;
|
||||
D3D11ContextStateGS gs;
|
||||
D3D11ContextStateHS hs;
|
||||
D3D11ContextStatePS ps;
|
||||
D3D11ContextStateVS vs;
|
||||
|
||||
Com<D3D11VertexShader, false> vs;
|
||||
Com<D3D11HullShader, false> hs;
|
||||
Com<D3D11DomainShader, false> ds;
|
||||
Com<D3D11GeometryShader, false> gs;
|
||||
Com<D3D11PixelShader, false> ps;
|
||||
Com<D3D11ComputeShader, false> cs;
|
||||
|
||||
D3D11ContextStateID id;
|
||||
D3D11ContextStateIA ia;
|
||||
D3D11ContextStateOM om;
|
||||
D3D11ContextStateRS rs;
|
||||
D3D11ContextStateSO so;
|
||||
D3D11ContextStatePR pr;
|
||||
|
||||
D3D11CbvBindings cbv;
|
||||
D3D11SrvBindings srv;
|
||||
D3D11UavBindings uav;
|
||||
D3D11SamplerBindings samplers;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* \brief Maximum used binding numbers in a shader stage
|
||||
*/
|
||||
struct D3D11MaxUsedStageBindings {
|
||||
uint32_t cbvCount : 5;
|
||||
uint32_t srvCount : 9;
|
||||
uint32_t uavCount : 7;
|
||||
uint32_t samplerCount : 5;
|
||||
uint32_t reserved : 6;
|
||||
};
|
||||
|
||||
/**
|
||||
* \brief Maximum used binding numbers for all context state
|
||||
*/
|
||||
struct D3D11MaxUsedBindings {
|
||||
std::array<D3D11MaxUsedStageBindings, 6> stages;
|
||||
uint32_t vbCount;
|
||||
uint32_t soCount;
|
||||
};
|
||||
|
||||
}
|
@ -37,12 +37,15 @@ namespace dxvk {
|
||||
|
||||
if (riid == __uuidof(ID3D10DeviceChild)
|
||||
|| riid == __uuidof(ID3D10DepthStencilState)) {
|
||||
*ppvObject = ref(this);
|
||||
*ppvObject = ref(&m_d3d10);
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
Logger::warn("D3D11DepthStencilState::QueryInterface: Unknown interface query");
|
||||
Logger::warn(str::format(riid));
|
||||
if (logQueryInterfaceError(__uuidof(ID3D11DepthStencilState), riid)) {
|
||||
Logger::warn("D3D11DepthStencilState::QueryInterface: Unknown interface query");
|
||||
Logger::warn(str::format(riid));
|
||||
}
|
||||
|
||||
return E_NOINTERFACE;
|
||||
}
|
||||
|
||||
@ -52,7 +55,7 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
void D3D11DepthStencilState::BindToContext(const Rc<DxvkContext>& ctx) {
|
||||
void D3D11DepthStencilState::BindToContext(DxvkContext* ctx) {
|
||||
ctx->setDepthStencilState(m_state);
|
||||
}
|
||||
|
||||
|
@ -29,8 +29,7 @@ namespace dxvk {
|
||||
void STDMETHODCALLTYPE GetDesc(
|
||||
D3D11_DEPTH_STENCIL_DESC* pDesc) final;
|
||||
|
||||
void BindToContext(
|
||||
const Rc<DxvkContext>& ctx);
|
||||
void BindToContext(DxvkContext* ctx);
|
||||
|
||||
D3D10DepthStencilState* GetD3D10Iface() {
|
||||
return &m_d3d10;
|
||||
|
@ -2,6 +2,7 @@
|
||||
#include <cstring>
|
||||
|
||||
#include "../dxgi/dxgi_monitor.h"
|
||||
#include "../dxgi/dxgi_surface.h"
|
||||
#include "../dxgi/dxgi_swapchain.h"
|
||||
|
||||
#include "../dxvk/dxvk_adapter.h"
|
||||
@ -12,6 +13,7 @@
|
||||
#include "d3d11_context_def.h"
|
||||
#include "d3d11_context_imm.h"
|
||||
#include "d3d11_device.h"
|
||||
#include "d3d11_fence.h"
|
||||
#include "d3d11_input_layout.h"
|
||||
#include "d3d11_interop.h"
|
||||
#include "d3d11_query.h"
|
||||
@ -23,6 +25,8 @@
|
||||
#include "d3d11_texture.h"
|
||||
#include "d3d11_video.h"
|
||||
|
||||
#include "../wsi/wsi_window.h"
|
||||
|
||||
#include "../util/util_shared_res.h"
|
||||
|
||||
namespace dxvk {
|
||||
@ -35,14 +39,16 @@ namespace dxvk {
|
||||
D3D11DXGIDevice* pContainer,
|
||||
D3D_FEATURE_LEVEL FeatureLevel,
|
||||
UINT FeatureFlags)
|
||||
: m_container (pContainer),
|
||||
m_featureLevel (FeatureLevel),
|
||||
m_featureFlags (FeatureFlags),
|
||||
m_dxvkDevice (pContainer->GetDXVKDevice()),
|
||||
m_dxvkAdapter (m_dxvkDevice->adapter()),
|
||||
m_d3d11Formats (m_dxvkAdapter),
|
||||
m_d3d11Options (m_dxvkDevice->instance()->config(), m_dxvkDevice),
|
||||
m_dxbcOptions (m_dxvkDevice, m_d3d11Options) {
|
||||
: m_container (pContainer),
|
||||
m_featureLevel (FeatureLevel),
|
||||
m_featureFlags (FeatureFlags),
|
||||
m_dxvkDevice (pContainer->GetDXVKDevice()),
|
||||
m_dxvkAdapter (m_dxvkDevice->adapter()),
|
||||
m_d3d11Formats (m_dxvkDevice),
|
||||
m_d3d11Options (m_dxvkDevice->instance()->config(), m_dxvkDevice),
|
||||
m_dxbcOptions (m_dxvkDevice, m_d3d11Options),
|
||||
m_maxFeatureLevel (GetMaxFeatureLevel(m_dxvkDevice->instance(), m_dxvkDevice->adapter())),
|
||||
m_deviceFeatures (m_dxvkDevice->instance(), m_dxvkDevice->adapter(), m_featureLevel) {
|
||||
m_initializer = new D3D11Initializer(this);
|
||||
m_context = new D3D11ImmediateContext(this, m_dxvkDevice);
|
||||
m_d3d10Device = new D3D10Device(this, m_context.ptr());
|
||||
@ -86,12 +92,19 @@ namespace dxvk {
|
||||
if (FAILED(hr))
|
||||
return hr;
|
||||
|
||||
if ((desc.MiscFlags & (D3D11_RESOURCE_MISC_TILED | D3D11_RESOURCE_MISC_TILE_POOL))
|
||||
&& !m_deviceFeatures.GetTiledResourcesTier())
|
||||
return E_INVALIDARG;
|
||||
|
||||
if (!ppBuffer)
|
||||
return S_FALSE;
|
||||
|
||||
try {
|
||||
const Com<D3D11Buffer> buffer = new D3D11Buffer(this, &desc);
|
||||
m_initializer->InitBuffer(buffer.ptr(), pInitialData);
|
||||
const Com<D3D11Buffer> buffer = new D3D11Buffer(this, &desc, nullptr);
|
||||
|
||||
if (!(desc.MiscFlags & D3D11_RESOURCE_MISC_TILE_POOL))
|
||||
m_initializer->InitBuffer(buffer.ptr(), pInitialData);
|
||||
|
||||
*ppBuffer = buffer.ref();
|
||||
return S_OK;
|
||||
} catch (const DxvkError& e) {
|
||||
@ -128,12 +141,15 @@ namespace dxvk {
|
||||
|
||||
if (FAILED(hr))
|
||||
return hr;
|
||||
|
||||
|
||||
if (desc.MiscFlags & D3D11_RESOURCE_MISC_TILED)
|
||||
return E_INVALIDARG;
|
||||
|
||||
if (!ppTexture1D)
|
||||
return S_FALSE;
|
||||
|
||||
try {
|
||||
const Com<D3D11Texture1D> texture = new D3D11Texture1D(this, &desc);
|
||||
const Com<D3D11Texture1D> texture = new D3D11Texture1D(this, &desc, nullptr);
|
||||
m_initializer->InitTexture(texture->GetCommonTexture(), pInitialData);
|
||||
*ppTexture1D = texture.ref();
|
||||
return S_OK;
|
||||
@ -202,6 +218,10 @@ namespace dxvk {
|
||||
|
||||
HRESULT hr = D3D11CommonTexture::NormalizeTextureProperties(&desc);
|
||||
|
||||
if ((desc.MiscFlags & D3D11_RESOURCE_MISC_TILED)
|
||||
&& !m_deviceFeatures.GetTiledResourcesTier())
|
||||
return E_INVALIDARG;
|
||||
|
||||
if (FAILED(hr))
|
||||
return hr;
|
||||
|
||||
@ -209,7 +229,7 @@ namespace dxvk {
|
||||
return S_FALSE;
|
||||
|
||||
try {
|
||||
Com<D3D11Texture2D> texture = new D3D11Texture2D(this, &desc, nullptr);
|
||||
Com<D3D11Texture2D> texture = new D3D11Texture2D(this, &desc, nullptr, nullptr);
|
||||
m_initializer->InitTexture(texture->GetCommonTexture(), pInitialData);
|
||||
*ppTexture2D = texture.ref();
|
||||
return S_OK;
|
||||
@ -279,12 +299,16 @@ namespace dxvk {
|
||||
|
||||
if (FAILED(hr))
|
||||
return hr;
|
||||
|
||||
|
||||
if ((desc.MiscFlags & D3D11_RESOURCE_MISC_TILED)
|
||||
&& (m_deviceFeatures.GetTiledResourcesTier() < D3D11_TILED_RESOURCES_TIER_3))
|
||||
return E_INVALIDARG;
|
||||
|
||||
if (!ppTexture3D)
|
||||
return S_FALSE;
|
||||
|
||||
try {
|
||||
Com<D3D11Texture3D> texture = new D3D11Texture3D(this, &desc);
|
||||
Com<D3D11Texture3D> texture = new D3D11Texture3D(this, &desc, nullptr);
|
||||
m_initializer->InitTexture(texture->GetCommonTexture(), pInitialData);
|
||||
*ppTexture3D = texture.ref();
|
||||
return S_OK;
|
||||
@ -590,7 +614,10 @@ namespace dxvk {
|
||||
ID3D11InputLayout** ppInputLayout) {
|
||||
InitReturnPtr(ppInputLayout);
|
||||
|
||||
if (pInputElementDescs == nullptr)
|
||||
// This check is somehow even correct, passing null with zero
|
||||
// size will always fail but passing non-null with zero size
|
||||
// works, provided the shader does not have any actual inputs
|
||||
if (!pInputElementDescs)
|
||||
return E_INVALIDARG;
|
||||
|
||||
try {
|
||||
@ -602,44 +629,39 @@ namespace dxvk {
|
||||
|
||||
uint32_t attrMask = 0;
|
||||
uint32_t bindMask = 0;
|
||||
uint32_t locationMask = 0;
|
||||
uint32_t bindingsDefined = 0;
|
||||
|
||||
std::array<DxvkVertexAttribute, D3D11_IA_VERTEX_INPUT_RESOURCE_SLOT_COUNT> attrList;
|
||||
std::array<DxvkVertexBinding, D3D11_IA_VERTEX_INPUT_RESOURCE_SLOT_COUNT> bindList;
|
||||
std::array<DxvkVertexAttribute, D3D11_IA_VERTEX_INPUT_RESOURCE_SLOT_COUNT> attrList = { };
|
||||
std::array<DxvkVertexBinding, D3D11_IA_VERTEX_INPUT_RESOURCE_SLOT_COUNT> bindList = { };
|
||||
|
||||
for (uint32_t i = 0; i < NumElements; i++) {
|
||||
const DxbcSgnEntry* entry = inputSignature->find(
|
||||
pInputElementDescs[i].SemanticName,
|
||||
pInputElementDescs[i].SemanticIndex, 0);
|
||||
|
||||
if (entry == nullptr) {
|
||||
Logger::debug(str::format(
|
||||
"D3D11Device: No such vertex shader semantic: ",
|
||||
pInputElementDescs[i].SemanticName,
|
||||
pInputElementDescs[i].SemanticIndex));
|
||||
}
|
||||
|
||||
|
||||
// Create vertex input attribute description
|
||||
DxvkVertexAttribute attrib;
|
||||
attrib.location = entry != nullptr ? entry->registerId : 0;
|
||||
attrib.binding = pInputElementDescs[i].InputSlot;
|
||||
attrib.format = LookupFormat(pInputElementDescs[i].Format, DXGI_VK_FORMAT_MODE_COLOR).Format;
|
||||
attrib.offset = pInputElementDescs[i].AlignedByteOffset;
|
||||
|
||||
|
||||
// The application may choose to let the implementation
|
||||
// generate the exact vertex layout. In that case we'll
|
||||
// pack attributes on the same binding in the order they
|
||||
// are declared, aligning each attribute to four bytes.
|
||||
const DxvkFormatInfo* formatInfo = imageFormatInfo(attrib.format);
|
||||
const DxvkFormatInfo* formatInfo = lookupFormatInfo(attrib.format);
|
||||
VkDeviceSize alignment = std::min<VkDeviceSize>(formatInfo->elementSize, 4);
|
||||
|
||||
if (attrib.offset == D3D11_APPEND_ALIGNED_ELEMENT) {
|
||||
attrib.offset = 0;
|
||||
|
||||
|
||||
for (uint32_t j = 1; j <= i; j++) {
|
||||
const DxvkVertexAttribute& prev = attrList.at(i - j);
|
||||
|
||||
|
||||
if (prev.binding == attrib.binding) {
|
||||
attrib.offset = align(prev.offset + imageFormatInfo(prev.format)->elementSize, alignment);
|
||||
attrib.offset = align(prev.offset + lookupFormatInfo(prev.format)->elementSize, alignment);
|
||||
break;
|
||||
}
|
||||
}
|
||||
@ -647,7 +669,7 @@ namespace dxvk {
|
||||
return E_INVALIDARG;
|
||||
|
||||
attrList.at(i) = attrib;
|
||||
|
||||
|
||||
// Create vertex input binding description. The
|
||||
// stride is dynamic state in D3D11 and will be
|
||||
// set by D3D11DeviceContext::IASetVertexBuffers.
|
||||
@ -656,66 +678,49 @@ namespace dxvk {
|
||||
binding.fetchRate = pInputElementDescs[i].InstanceDataStepRate;
|
||||
binding.inputRate = pInputElementDescs[i].InputSlotClass == D3D11_INPUT_PER_INSTANCE_DATA
|
||||
? VK_VERTEX_INPUT_RATE_INSTANCE : VK_VERTEX_INPUT_RATE_VERTEX;
|
||||
|
||||
binding.extent = entry ? uint32_t(attrib.offset + formatInfo->elementSize) : 0u;
|
||||
|
||||
// Check if the binding was already defined. If so, the
|
||||
// parameters must be identical (namely, the input rate).
|
||||
bool bindingDefined = false;
|
||||
|
||||
for (uint32_t j = 0; j < i; j++) {
|
||||
uint32_t bindingId = attrList.at(j).binding;
|
||||
if (bindingsDefined & (1u << binding.binding)) {
|
||||
if (bindList.at(binding.binding).inputRate != binding.inputRate)
|
||||
return E_INVALIDARG;
|
||||
|
||||
if (binding.binding == bindingId) {
|
||||
bindingDefined = true;
|
||||
|
||||
if (binding.inputRate != bindList.at(bindingId).inputRate) {
|
||||
Logger::err(str::format(
|
||||
"D3D11Device: Conflicting input rate for binding ",
|
||||
binding.binding));
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
}
|
||||
bindList.at(binding.binding).extent = std::max(
|
||||
bindList.at(binding.binding).extent, binding.extent);
|
||||
} else {
|
||||
bindList.at(binding.binding) = binding;
|
||||
bindingsDefined |= 1u << binding.binding;
|
||||
}
|
||||
|
||||
if (!bindingDefined)
|
||||
bindList.at(binding.binding) = binding;
|
||||
|
||||
if (entry != nullptr) {
|
||||
if (entry) {
|
||||
attrMask |= 1u << i;
|
||||
bindMask |= 1u << binding.binding;
|
||||
locationMask |= 1u << attrib.location;
|
||||
}
|
||||
}
|
||||
|
||||
// Ensure that all inputs used by the shader are defined
|
||||
for (auto i = inputSignature->begin(); i != inputSignature->end(); i++) {
|
||||
bool isBuiltIn = DxbcIsgn::compareSemanticNames(i->semanticName, "sv_instanceid")
|
||||
|| DxbcIsgn::compareSemanticNames(i->semanticName, "sv_vertexid");
|
||||
|
||||
if (!isBuiltIn && !(locationMask & (1u << i->registerId)))
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
|
||||
// Compact the attribute and binding lists to filter
|
||||
// out attributes and bindings not used by the shader
|
||||
uint32_t attrCount = CompactSparseList(attrList.data(), attrMask);
|
||||
uint32_t bindCount = CompactSparseList(bindList.data(), bindMask);
|
||||
|
||||
// Check if there are any semantics defined in the
|
||||
// shader that are not included in the current input
|
||||
// layout.
|
||||
for (auto i = inputSignature->begin(); i != inputSignature->end(); i++) {
|
||||
bool found = i->systemValue != DxbcSystemValue::None;
|
||||
|
||||
for (uint32_t j = 0; j < attrCount && !found; j++)
|
||||
found = attrList.at(j).location == i->registerId;
|
||||
|
||||
if (!found) {
|
||||
Logger::warn(str::format(
|
||||
"D3D11Device: Vertex input '",
|
||||
i->semanticName, i->semanticIndex,
|
||||
"' not defined by input layout"));
|
||||
}
|
||||
}
|
||||
|
||||
// Create the actual input layout object
|
||||
// if the application requests it.
|
||||
if (ppInputLayout != nullptr) {
|
||||
*ppInputLayout = ref(
|
||||
new D3D11InputLayout(this,
|
||||
attrCount, attrList.data(),
|
||||
bindCount, bindList.data()));
|
||||
}
|
||||
|
||||
if (!ppInputLayout)
|
||||
return S_FALSE;
|
||||
|
||||
*ppInputLayout = ref(
|
||||
new D3D11InputLayout(this,
|
||||
attrCount, attrList.data(),
|
||||
bindCount, bindList.data()));
|
||||
return S_OK;
|
||||
} catch (const DxvkError& e) {
|
||||
Logger::err(e.message());
|
||||
@ -1141,7 +1146,7 @@ namespace dxvk {
|
||||
return E_INVALIDARG;
|
||||
|
||||
if (desc.ConservativeRaster != D3D11_CONSERVATIVE_RASTERIZATION_MODE_OFF
|
||||
&& !m_dxvkDevice->extensions().extConservativeRasterization)
|
||||
&& !m_deviceFeatures.GetConservativeRasterizationTier())
|
||||
return E_INVALIDARG;
|
||||
|
||||
if (!ppRasterizerState)
|
||||
@ -1164,8 +1169,13 @@ namespace dxvk {
|
||||
|
||||
if (FAILED(D3D11SamplerState::NormalizeDesc(&desc)))
|
||||
return E_INVALIDARG;
|
||||
|
||||
if (ppSamplerState == nullptr)
|
||||
|
||||
D3D11_TILED_RESOURCES_TIER tiledResourcesTier = m_deviceFeatures.GetTiledResourcesTier();
|
||||
|
||||
if (IsMinMaxFilter(desc.Filter) && tiledResourcesTier < D3D11_TILED_RESOURCES_TIER_2)
|
||||
return E_INVALIDARG;
|
||||
|
||||
if (!ppSamplerState)
|
||||
return S_FALSE;
|
||||
|
||||
try {
|
||||
@ -1312,33 +1322,41 @@ namespace dxvk {
|
||||
ID3DDeviceContextState** ppContextState) {
|
||||
InitReturnPtr(ppContextState);
|
||||
|
||||
if (!pFeatureLevels || FeatureLevels == 0)
|
||||
if (!pFeatureLevels || !FeatureLevels)
|
||||
return E_INVALIDARG;
|
||||
|
||||
|
||||
if (EmulatedInterface != __uuidof(ID3D10Device)
|
||||
&& EmulatedInterface != __uuidof(ID3D10Device1)
|
||||
&& EmulatedInterface != __uuidof(ID3D11Device)
|
||||
&& EmulatedInterface != __uuidof(ID3D11Device1))
|
||||
return E_INVALIDARG;
|
||||
|
||||
UINT flId;
|
||||
for (flId = 0; flId < FeatureLevels; flId++) {
|
||||
if (CheckFeatureLevelSupport(m_dxvkDevice->instance(), m_dxvkAdapter, pFeatureLevels[flId]))
|
||||
|
||||
D3D_FEATURE_LEVEL featureLevel = D3D_FEATURE_LEVEL();
|
||||
|
||||
for (uint32_t flId = 0; flId < FeatureLevels; flId++) {
|
||||
if (pFeatureLevels[flId] <= m_maxFeatureLevel) {
|
||||
featureLevel = pFeatureLevels[flId];
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (flId == FeatureLevels)
|
||||
if (!featureLevel)
|
||||
return E_INVALIDARG;
|
||||
|
||||
if (pFeatureLevels[flId] > m_featureLevel)
|
||||
m_featureLevel = pFeatureLevels[flId];
|
||||
|
||||
if (m_featureLevel < featureLevel) {
|
||||
m_featureLevel = featureLevel;
|
||||
m_deviceFeatures = D3D11DeviceFeatures(
|
||||
m_dxvkDevice->instance(),
|
||||
m_dxvkDevice->adapter(),
|
||||
m_featureLevel);
|
||||
}
|
||||
|
||||
if (pChosenFeatureLevel)
|
||||
*pChosenFeatureLevel = pFeatureLevels[flId];
|
||||
|
||||
*pChosenFeatureLevel = featureLevel;
|
||||
|
||||
if (!ppContextState)
|
||||
return S_FALSE;
|
||||
|
||||
|
||||
*ppContextState = ref(new D3D11DeviceContextState(this));
|
||||
return S_OK;
|
||||
}
|
||||
@ -1347,16 +1365,17 @@ namespace dxvk {
|
||||
HRESULT STDMETHODCALLTYPE D3D11Device::CreateFence(
|
||||
UINT64 InitialValue,
|
||||
D3D11_FENCE_FLAG Flags,
|
||||
REFIID ReturnedInterface,
|
||||
REFIID riid,
|
||||
void** ppFence) {
|
||||
InitReturnPtr(ppFence);
|
||||
|
||||
static bool s_errorShown = false;
|
||||
|
||||
if (!std::exchange(s_errorShown, true))
|
||||
Logger::err("D3D11Device::CreateFence: Not implemented");
|
||||
|
||||
return E_NOTIMPL;
|
||||
try {
|
||||
Com<D3D11Fence> fence = new D3D11Fence(this, InitialValue, Flags, INVALID_HANDLE_VALUE);
|
||||
return fence->QueryInterface(riid, ppFence);
|
||||
} catch (const DxvkError& e) {
|
||||
Logger::err(e.message());
|
||||
return E_FAIL;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -1367,9 +1386,25 @@ namespace dxvk {
|
||||
ID3D11Resource* pSrcResource,
|
||||
UINT SrcSubresource,
|
||||
const D3D11_BOX* pSrcBox) {
|
||||
auto texture = GetCommonTexture(pSrcResource);
|
||||
|
||||
if (!texture)
|
||||
return;
|
||||
|
||||
if (texture->Desc()->Usage != D3D11_USAGE_DEFAULT
|
||||
|| texture->GetMapMode() == D3D11_COMMON_TEXTURE_MAP_MODE_NONE
|
||||
|| texture->CountSubresources() <= SrcSubresource)
|
||||
return;
|
||||
|
||||
D3D11_MAP map = texture->GetMapType(SrcSubresource);
|
||||
|
||||
if (map != D3D11_MAP_READ
|
||||
&& map != D3D11_MAP_READ_WRITE)
|
||||
return;
|
||||
|
||||
CopySubresourceData(
|
||||
pDstData, DstRowPitch, DstDepthPitch,
|
||||
pSrcResource, SrcSubresource, pSrcBox);
|
||||
texture, SrcSubresource, pSrcBox);
|
||||
}
|
||||
|
||||
|
||||
@ -1380,9 +1415,26 @@ namespace dxvk {
|
||||
const void* pSrcData,
|
||||
UINT SrcRowPitch,
|
||||
UINT SrcDepthPitch) {
|
||||
auto texture = GetCommonTexture(pDstResource);
|
||||
|
||||
if (!texture)
|
||||
return;
|
||||
|
||||
if (texture->Desc()->Usage != D3D11_USAGE_DEFAULT
|
||||
|| texture->GetMapMode() == D3D11_COMMON_TEXTURE_MAP_MODE_NONE
|
||||
|| texture->CountSubresources() <= DstSubresource)
|
||||
return;
|
||||
|
||||
D3D11_MAP map = texture->GetMapType(DstSubresource);
|
||||
|
||||
if (map != D3D11_MAP_WRITE
|
||||
&& map != D3D11_MAP_WRITE_NO_OVERWRITE
|
||||
&& map != D3D11_MAP_READ_WRITE)
|
||||
return;
|
||||
|
||||
CopySubresourceData(
|
||||
pSrcData, SrcRowPitch, SrcRowPitch,
|
||||
pDstResource, DstSubresource, pDstBox);
|
||||
texture, DstSubresource, pDstBox);
|
||||
}
|
||||
|
||||
|
||||
@ -1422,8 +1474,16 @@ namespace dxvk {
|
||||
void** ppFence) {
|
||||
InitReturnPtr(ppFence);
|
||||
|
||||
Logger::err("D3D11Device::OpenSharedFence: Not implemented");
|
||||
return E_NOTIMPL;
|
||||
if (ppFence == nullptr)
|
||||
return S_FALSE;
|
||||
|
||||
try {
|
||||
Com<D3D11Fence> fence = new D3D11Fence(this, 0, D3D11_FENCE_FLAG_SHARED, hFence);
|
||||
return fence->QueryInterface(ReturnedInterface, ppFence);
|
||||
} catch (const DxvkError& e) {
|
||||
Logger::err(e.message());
|
||||
return E_FAIL;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -1482,17 +1542,29 @@ namespace dxvk {
|
||||
|
||||
if (FAILED(DecodeSampleCount(SampleCount, &sampleCountFlag)))
|
||||
return SampleCount && SampleCount <= 32 ? S_OK : E_FAIL;
|
||||
|
||||
|
||||
// Get image create flags depending on function arguments
|
||||
VkImageCreateFlags flags = 0;
|
||||
|
||||
if (Flags & D3D11_CHECK_MULTISAMPLE_QUALITY_LEVELS_TILED_RESOURCE) {
|
||||
flags |= VK_IMAGE_CREATE_SPARSE_BINDING_BIT
|
||||
| VK_IMAGE_CREATE_SPARSE_RESIDENCY_BIT
|
||||
| VK_IMAGE_CREATE_SPARSE_ALIASED_BIT;
|
||||
}
|
||||
|
||||
// Check if the device supports the given combination of format
|
||||
// and sample count. D3D exposes the opaque concept of quality
|
||||
// levels to the application, we'll just define one such level.
|
||||
VkImageFormatProperties formatProps;
|
||||
|
||||
VkResult status = m_dxvkAdapter->imageFormatProperties(
|
||||
format, VK_IMAGE_TYPE_2D, VK_IMAGE_TILING_OPTIMAL,
|
||||
VK_IMAGE_USAGE_SAMPLED_BIT, 0, formatProps);
|
||||
|
||||
if ((status == VK_SUCCESS) && (formatProps.sampleCounts & sampleCountFlag))
|
||||
DxvkFormatQuery formatQuery = { };
|
||||
formatQuery.format = format;
|
||||
formatQuery.type = VK_IMAGE_TYPE_2D;
|
||||
formatQuery.tiling = VK_IMAGE_TILING_OPTIMAL;
|
||||
formatQuery.usage = VK_IMAGE_USAGE_SAMPLED_BIT;
|
||||
formatQuery.flags = flags;
|
||||
|
||||
auto properties = m_dxvkDevice->getFormatLimits(formatQuery);
|
||||
|
||||
if (properties && (properties->sampleCounts & sampleCountFlag))
|
||||
*pNumQualityLevels = 1;
|
||||
return S_OK;
|
||||
}
|
||||
@ -1526,29 +1598,8 @@ namespace dxvk {
|
||||
void* pFeatureSupportData,
|
||||
UINT FeatureSupportDataSize) {
|
||||
switch (Feature) {
|
||||
case D3D11_FEATURE_THREADING: {
|
||||
auto info = static_cast<D3D11_FEATURE_DATA_THREADING*>(pFeatureSupportData);
|
||||
|
||||
if (FeatureSupportDataSize != sizeof(*info))
|
||||
return E_INVALIDARG;
|
||||
|
||||
// We report native support for command lists here so that we do not actually
|
||||
// have to re-implement the UpdateSubresource bug from the D3D11 runtime, see
|
||||
// https://msdn.microsoft.com/en-us/library/windows/desktop/ff476486(v=vs.85).aspx)
|
||||
info->DriverConcurrentCreates = TRUE;
|
||||
info->DriverCommandLists = TRUE;
|
||||
} return S_OK;
|
||||
|
||||
case D3D11_FEATURE_DOUBLES: {
|
||||
auto info = static_cast<D3D11_FEATURE_DATA_DOUBLES*>(pFeatureSupportData);
|
||||
|
||||
if (FeatureSupportDataSize != sizeof(*info))
|
||||
return E_INVALIDARG;
|
||||
|
||||
info->DoublePrecisionFloatShaderOps = m_dxvkDevice->features().core.features.shaderFloat64
|
||||
&& m_dxvkDevice->features().core.features.shaderInt64;
|
||||
} return S_OK;
|
||||
|
||||
// Format support queries are special in that they use in-out
|
||||
// structs, and we need the Vulkan device to query them at all
|
||||
case D3D11_FEATURE_FORMAT_SUPPORT: {
|
||||
auto info = static_cast<D3D11_FEATURE_DATA_FORMAT_SUPPORT*>(pFeatureSupportData);
|
||||
|
||||
@ -1557,7 +1608,7 @@ namespace dxvk {
|
||||
|
||||
return GetFormatSupportFlags(info->InFormat, &info->OutFormatSupport, nullptr);
|
||||
} return S_OK;
|
||||
|
||||
|
||||
case D3D11_FEATURE_FORMAT_SUPPORT2: {
|
||||
auto info = static_cast<D3D11_FEATURE_DATA_FORMAT_SUPPORT2*>(pFeatureSupportData);
|
||||
|
||||
@ -1566,181 +1617,11 @@ namespace dxvk {
|
||||
|
||||
return GetFormatSupportFlags(info->InFormat, nullptr, &info->OutFormatSupport2);
|
||||
} return S_OK;
|
||||
|
||||
case D3D11_FEATURE_D3D10_X_HARDWARE_OPTIONS: {
|
||||
auto info = static_cast<D3D11_FEATURE_DATA_D3D10_X_HARDWARE_OPTIONS*>(pFeatureSupportData);
|
||||
|
||||
if (FeatureSupportDataSize != sizeof(*info))
|
||||
return E_INVALIDARG;
|
||||
|
||||
info->ComputeShaders_Plus_RawAndStructuredBuffers_Via_Shader_4_x = TRUE;
|
||||
} return S_OK;
|
||||
|
||||
case D3D11_FEATURE_D3D11_OPTIONS: {
|
||||
auto info = static_cast<D3D11_FEATURE_DATA_D3D11_OPTIONS*>(pFeatureSupportData);
|
||||
|
||||
if (FeatureSupportDataSize != sizeof(*info))
|
||||
return E_INVALIDARG;
|
||||
|
||||
// https://msdn.microsoft.com/en-us/library/windows/desktop/hh404457(v=vs.85).aspx
|
||||
const auto& features = m_dxvkDevice->features();
|
||||
|
||||
info->OutputMergerLogicOp = features.core.features.logicOp;
|
||||
info->UAVOnlyRenderingForcedSampleCount = features.core.features.variableMultisampleRate;
|
||||
info->DiscardAPIsSeenByDriver = TRUE;
|
||||
info->FlagsForUpdateAndCopySeenByDriver = TRUE;
|
||||
info->ClearView = TRUE;
|
||||
info->CopyWithOverlap = TRUE;
|
||||
info->ConstantBufferPartialUpdate = TRUE;
|
||||
info->ConstantBufferOffsetting = TRUE;
|
||||
info->MapNoOverwriteOnDynamicConstantBuffer = TRUE;
|
||||
info->MapNoOverwriteOnDynamicBufferSRV = TRUE;
|
||||
info->MultisampleRTVWithForcedSampleCountOne = TRUE; /* not really */
|
||||
info->SAD4ShaderInstructions = TRUE;
|
||||
info->ExtendedDoublesShaderInstructions = TRUE;
|
||||
info->ExtendedResourceSharing = TRUE; /* not really */
|
||||
} return S_OK;
|
||||
|
||||
case D3D11_FEATURE_ARCHITECTURE_INFO: {
|
||||
auto info = static_cast<D3D11_FEATURE_DATA_ARCHITECTURE_INFO*>(pFeatureSupportData);
|
||||
|
||||
if (FeatureSupportDataSize != sizeof(*info))
|
||||
return E_INVALIDARG;
|
||||
|
||||
info->TileBasedDeferredRenderer = FALSE;
|
||||
} return S_OK;
|
||||
|
||||
case D3D11_FEATURE_D3D9_OPTIONS: {
|
||||
auto info = static_cast<D3D11_FEATURE_DATA_D3D9_OPTIONS*>(pFeatureSupportData);
|
||||
|
||||
if (FeatureSupportDataSize != sizeof(*info))
|
||||
return E_INVALIDARG;
|
||||
|
||||
info->FullNonPow2TextureSupport = TRUE;
|
||||
} return S_OK;
|
||||
|
||||
case D3D11_FEATURE_SHADER_MIN_PRECISION_SUPPORT: {
|
||||
auto info = static_cast<D3D11_FEATURE_DATA_SHADER_MIN_PRECISION_SUPPORT*>(pFeatureSupportData);
|
||||
|
||||
if (FeatureSupportDataSize != sizeof(*info))
|
||||
return E_INVALIDARG;
|
||||
|
||||
// Report that we only support full 32-bit operations
|
||||
info->PixelShaderMinPrecision = 0;
|
||||
info->AllOtherShaderStagesMinPrecision = 0;
|
||||
} return S_OK;
|
||||
|
||||
case D3D11_FEATURE_D3D9_SHADOW_SUPPORT: {
|
||||
auto info = static_cast<D3D11_FEATURE_DATA_D3D9_SHADOW_SUPPORT*>(pFeatureSupportData);
|
||||
|
||||
if (FeatureSupportDataSize != sizeof(*info))
|
||||
return E_INVALIDARG;
|
||||
|
||||
info->SupportsDepthAsTextureWithLessEqualComparisonFilter = TRUE;
|
||||
} return S_OK;
|
||||
|
||||
case D3D11_FEATURE_D3D11_OPTIONS1: {
|
||||
auto info = static_cast<D3D11_FEATURE_DATA_D3D11_OPTIONS1*>(pFeatureSupportData);
|
||||
|
||||
if (FeatureSupportDataSize != sizeof(*info))
|
||||
return E_INVALIDARG;
|
||||
|
||||
// Min/Max filtering requires Tiled Resources Tier 2 for some reason,
|
||||
// so we cannot support it even though Vulkan exposes this feature
|
||||
info->TiledResourcesTier = D3D11_TILED_RESOURCES_NOT_SUPPORTED;
|
||||
info->MinMaxFiltering = FALSE;
|
||||
info->ClearViewAlsoSupportsDepthOnlyFormats = TRUE;
|
||||
info->MapOnDefaultBuffers = TRUE;
|
||||
} return S_OK;
|
||||
|
||||
case D3D11_FEATURE_D3D9_SIMPLE_INSTANCING_SUPPORT: {
|
||||
auto info = static_cast<D3D11_FEATURE_DATA_D3D9_SIMPLE_INSTANCING_SUPPORT*>(pFeatureSupportData);
|
||||
|
||||
if (FeatureSupportDataSize != sizeof(*info))
|
||||
return E_INVALIDARG;
|
||||
|
||||
info->SimpleInstancingSupported = TRUE;
|
||||
} return S_OK;
|
||||
|
||||
case D3D11_FEATURE_MARKER_SUPPORT: {
|
||||
auto info = static_cast<D3D11_FEATURE_DATA_MARKER_SUPPORT*>(pFeatureSupportData);
|
||||
|
||||
if (FeatureSupportDataSize != sizeof(*info))
|
||||
return E_INVALIDARG;
|
||||
|
||||
info->Profile = FALSE;
|
||||
} return S_OK;
|
||||
|
||||
case D3D11_FEATURE_D3D9_OPTIONS1: {
|
||||
auto info = static_cast<D3D11_FEATURE_DATA_D3D9_OPTIONS1*>(pFeatureSupportData);
|
||||
|
||||
if (FeatureSupportDataSize != sizeof(*info))
|
||||
return E_INVALIDARG;
|
||||
|
||||
info->FullNonPow2TextureSupported = TRUE;
|
||||
info->DepthAsTextureWithLessEqualComparisonFilterSupported = TRUE;
|
||||
info->SimpleInstancingSupported = TRUE;
|
||||
info->TextureCubeFaceRenderTargetWithNonCubeDepthStencilSupported = TRUE;
|
||||
} return S_OK;
|
||||
|
||||
case D3D11_FEATURE_D3D11_OPTIONS2: {
|
||||
auto info = static_cast<D3D11_FEATURE_DATA_D3D11_OPTIONS2*>(pFeatureSupportData);
|
||||
|
||||
if (FeatureSupportDataSize != sizeof(*info))
|
||||
return E_INVALIDARG;
|
||||
|
||||
const auto& extensions = m_dxvkDevice->extensions();
|
||||
const auto& features = m_dxvkDevice->features();
|
||||
|
||||
info->PSSpecifiedStencilRefSupported = extensions.extShaderStencilExport;
|
||||
info->TypedUAVLoadAdditionalFormats = features.core.features.shaderStorageImageReadWithoutFormat;
|
||||
info->ROVsSupported = FALSE;
|
||||
info->ConservativeRasterizationTier = D3D11_CONSERVATIVE_RASTERIZATION_NOT_SUPPORTED;
|
||||
info->MapOnDefaultTextures = TRUE;
|
||||
info->TiledResourcesTier = D3D11_TILED_RESOURCES_NOT_SUPPORTED;
|
||||
info->StandardSwizzle = FALSE;
|
||||
info->UnifiedMemoryArchitecture = m_dxvkDevice->isUnifiedMemoryArchitecture();
|
||||
|
||||
if (m_dxvkDevice->extensions().extConservativeRasterization) {
|
||||
// We don't have a way to query uncertainty regions, so just check degenerate triangle behaviour
|
||||
info->ConservativeRasterizationTier = m_dxvkDevice->properties().extConservativeRasterization.degenerateTrianglesRasterized
|
||||
? D3D11_CONSERVATIVE_RASTERIZATION_TIER_2 : D3D11_CONSERVATIVE_RASTERIZATION_TIER_1;
|
||||
}
|
||||
} return S_OK;
|
||||
|
||||
case D3D11_FEATURE_D3D11_OPTIONS3: {
|
||||
if (FeatureSupportDataSize != sizeof(D3D11_FEATURE_DATA_D3D11_OPTIONS3))
|
||||
return E_INVALIDARG;
|
||||
|
||||
const auto& extensions = m_dxvkDevice->extensions();
|
||||
|
||||
auto info = static_cast<D3D11_FEATURE_DATA_D3D11_OPTIONS3*>(pFeatureSupportData);
|
||||
info->VPAndRTArrayIndexFromAnyShaderFeedingRasterizer = extensions.extShaderViewportIndexLayer;
|
||||
} return S_OK;
|
||||
|
||||
case D3D11_FEATURE_GPU_VIRTUAL_ADDRESS_SUPPORT: {
|
||||
auto info = static_cast<D3D11_FEATURE_DATA_GPU_VIRTUAL_ADDRESS_SUPPORT*>(pFeatureSupportData);
|
||||
|
||||
if (FeatureSupportDataSize != sizeof(*info))
|
||||
return E_INVALIDARG;
|
||||
|
||||
// These numbers are not accurate, but it should not have any effect on D3D11 apps
|
||||
info->MaxGPUVirtualAddressBitsPerResource = 32;
|
||||
info->MaxGPUVirtualAddressBitsPerProcess = 40;
|
||||
} return S_OK;
|
||||
|
||||
case D3D11_FEATURE_D3D11_OPTIONS4: {
|
||||
auto info = static_cast<D3D11_FEATURE_DATA_D3D11_OPTIONS4*>(pFeatureSupportData);
|
||||
|
||||
if (FeatureSupportDataSize != sizeof(*info))
|
||||
return E_INVALIDARG;
|
||||
|
||||
info->ExtendedNV12SharedTextureSupported = FALSE;
|
||||
} return S_OK;
|
||||
|
||||
default:
|
||||
Logger::err(str::format("D3D11Device: CheckFeatureSupport: Unknown feature: ", Feature));
|
||||
return E_INVALIDARG;
|
||||
// For everything else, we can use the device feature struct
|
||||
// that we already initialized during device creation.
|
||||
return m_deviceFeatures.GetFeatureData(Feature, FeatureSupportDataSize, pFeatureSupportData);
|
||||
}
|
||||
}
|
||||
|
||||
@ -1823,27 +1704,90 @@ namespace dxvk {
|
||||
UINT* pNumSubresourceTilings,
|
||||
UINT FirstSubresourceTilingToGet,
|
||||
D3D11_SUBRESOURCE_TILING* pSubresourceTilingsForNonPackedMips) {
|
||||
static bool s_errorShown = false;
|
||||
D3D11_COMMON_RESOURCE_DESC desc = { };
|
||||
GetCommonResourceDesc(pTiledResource, &desc);
|
||||
|
||||
if (!std::exchange(s_errorShown, true))
|
||||
Logger::err("D3D11Device::GetResourceTiling: Tiled resources not supported");
|
||||
if (!(desc.MiscFlags & D3D11_RESOURCE_MISC_TILED)) {
|
||||
if (pNumTilesForEntireResource)
|
||||
*pNumTilesForEntireResource = 0;
|
||||
|
||||
if (pNumTilesForEntireResource)
|
||||
*pNumTilesForEntireResource = 0;
|
||||
if (pPackedMipDesc)
|
||||
*pPackedMipDesc = D3D11_PACKED_MIP_DESC();
|
||||
|
||||
if (pPackedMipDesc)
|
||||
*pPackedMipDesc = D3D11_PACKED_MIP_DESC();
|
||||
if (pStandardTileShapeForNonPackedMips)
|
||||
*pStandardTileShapeForNonPackedMips = D3D11_TILE_SHAPE();
|
||||
|
||||
if (pStandardTileShapeForNonPackedMips)
|
||||
*pStandardTileShapeForNonPackedMips = D3D11_TILE_SHAPE();
|
||||
if (pNumSubresourceTilings) {
|
||||
if (pSubresourceTilingsForNonPackedMips) {
|
||||
for (uint32_t i = 0; i < *pNumSubresourceTilings; i++)
|
||||
pSubresourceTilingsForNonPackedMips[i] = D3D11_SUBRESOURCE_TILING();
|
||||
}
|
||||
|
||||
if (pNumSubresourceTilings) {
|
||||
if (pSubresourceTilingsForNonPackedMips) {
|
||||
for (uint32_t i = 0; i < *pNumSubresourceTilings; i++)
|
||||
pSubresourceTilingsForNonPackedMips[i] = D3D11_SUBRESOURCE_TILING();
|
||||
*pNumSubresourceTilings = 0;
|
||||
}
|
||||
} else {
|
||||
DxvkSparsePageTable* sparseInfo = nullptr;
|
||||
uint32_t mipCount = 0;
|
||||
|
||||
if (desc.Dim == D3D11_RESOURCE_DIMENSION_BUFFER) {
|
||||
Rc<DxvkBuffer> buffer = static_cast<D3D11Buffer*>(pTiledResource)->GetBuffer();
|
||||
sparseInfo = buffer->getSparsePageTable();
|
||||
} else {
|
||||
Rc<DxvkImage> image = GetCommonTexture(pTiledResource)->GetImage();
|
||||
sparseInfo = image->getSparsePageTable();
|
||||
mipCount = image->info().mipLevels;
|
||||
}
|
||||
|
||||
*pNumSubresourceTilings = 0;
|
||||
if (pNumTilesForEntireResource)
|
||||
*pNumTilesForEntireResource = sparseInfo->getPageCount();
|
||||
|
||||
if (pPackedMipDesc) {
|
||||
auto properties = sparseInfo->getProperties();
|
||||
|
||||
if (properties.mipTailSize) {
|
||||
pPackedMipDesc->NumStandardMips = properties.pagedMipCount;
|
||||
pPackedMipDesc->NumPackedMips = mipCount - properties.pagedMipCount;
|
||||
pPackedMipDesc->NumTilesForPackedMips = sparseInfo->getPageCount() - properties.mipTailPageIndex;
|
||||
pPackedMipDesc->StartTileIndexInOverallResource = properties.mipTailPageIndex;
|
||||
} else {
|
||||
pPackedMipDesc->NumStandardMips = mipCount;
|
||||
pPackedMipDesc->NumPackedMips = 0;
|
||||
pPackedMipDesc->NumTilesForPackedMips = 0;
|
||||
pPackedMipDesc->StartTileIndexInOverallResource = 0;
|
||||
}
|
||||
}
|
||||
|
||||
if (pStandardTileShapeForNonPackedMips) {
|
||||
auto properties = sparseInfo->getProperties();
|
||||
pStandardTileShapeForNonPackedMips->WidthInTexels = properties.pageRegionExtent.width;
|
||||
pStandardTileShapeForNonPackedMips->HeightInTexels = properties.pageRegionExtent.height;
|
||||
pStandardTileShapeForNonPackedMips->DepthInTexels = properties.pageRegionExtent.depth;
|
||||
}
|
||||
|
||||
if (pNumSubresourceTilings) {
|
||||
uint32_t subresourceCount = sparseInfo->getSubresourceCount();
|
||||
uint32_t tilingCount = subresourceCount - std::min(FirstSubresourceTilingToGet, subresourceCount);
|
||||
tilingCount = std::min(tilingCount, *pNumSubresourceTilings);
|
||||
|
||||
for (uint32_t i = 0; i < tilingCount; i++) {
|
||||
auto subresourceInfo = sparseInfo->getSubresourceProperties(FirstSubresourceTilingToGet + i);
|
||||
auto dstInfo = &pSubresourceTilingsForNonPackedMips[i];
|
||||
|
||||
if (subresourceInfo.isMipTail) {
|
||||
dstInfo->WidthInTiles = 0u;
|
||||
dstInfo->HeightInTiles = 0u;
|
||||
dstInfo->DepthInTiles = 0u;
|
||||
dstInfo->StartTileIndexInOverallResource = D3D11_PACKED_TILE;
|
||||
} else {
|
||||
dstInfo->WidthInTiles = subresourceInfo.pageCount.width;
|
||||
dstInfo->HeightInTiles = subresourceInfo.pageCount.height;
|
||||
dstInfo->DepthInTiles = subresourceInfo.pageCount.depth;
|
||||
dstInfo->StartTileIndexInOverallResource = subresourceInfo.pageIndex;
|
||||
}
|
||||
}
|
||||
|
||||
*pNumSubresourceTilings = tilingCount;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -1888,6 +1832,11 @@ namespace dxvk {
|
||||
DXGI_VK_FORMAT_MODE Mode) const {
|
||||
return m_d3d11Formats.GetFormatFamily(Format, Mode);
|
||||
}
|
||||
|
||||
|
||||
bool D3D11Device::Is11on12Device() const {
|
||||
return m_container->Is11on12Device();
|
||||
}
|
||||
|
||||
|
||||
void D3D11Device::FlushInitContext() {
|
||||
@ -1895,107 +1844,120 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
bool D3D11Device::CheckFeatureLevelSupport(
|
||||
const Rc<DxvkInstance>& instance,
|
||||
const Rc<DxvkAdapter>& adapter,
|
||||
D3D_FEATURE_LEVEL featureLevel) {
|
||||
if (featureLevel > GetMaxFeatureLevel(instance))
|
||||
return false;
|
||||
D3D_FEATURE_LEVEL D3D11Device::GetMaxFeatureLevel(
|
||||
const Rc<DxvkInstance>& Instance,
|
||||
const Rc<DxvkAdapter>& Adapter) {
|
||||
// Check whether baseline features are supported by the device
|
||||
DxvkDeviceFeatures features = GetDeviceFeatures(Adapter);
|
||||
|
||||
// Check whether all features are supported
|
||||
const DxvkDeviceFeatures features
|
||||
= GetDeviceFeatures(adapter, featureLevel);
|
||||
if (!Adapter->checkFeatureSupport(features))
|
||||
return D3D_FEATURE_LEVEL();
|
||||
|
||||
// The feature level override always takes precedence
|
||||
static const std::array<std::pair<std::string, D3D_FEATURE_LEVEL>, 9> s_featureLevels = {{
|
||||
{ "12_1", D3D_FEATURE_LEVEL_12_1 },
|
||||
{ "12_0", D3D_FEATURE_LEVEL_12_0 },
|
||||
{ "11_1", D3D_FEATURE_LEVEL_11_1 },
|
||||
{ "11_0", D3D_FEATURE_LEVEL_11_0 },
|
||||
{ "10_1", D3D_FEATURE_LEVEL_10_1 },
|
||||
{ "10_0", D3D_FEATURE_LEVEL_10_0 },
|
||||
{ "9_3", D3D_FEATURE_LEVEL_9_3 },
|
||||
{ "9_2", D3D_FEATURE_LEVEL_9_2 },
|
||||
{ "9_1", D3D_FEATURE_LEVEL_9_1 },
|
||||
}};
|
||||
|
||||
if (!adapter->checkFeatureSupport(features))
|
||||
return false;
|
||||
|
||||
// TODO also check for required limits
|
||||
return true;
|
||||
std::string maxLevel = Instance->config().getOption<std::string>("d3d11.maxFeatureLevel");
|
||||
|
||||
auto entry = std::find_if(s_featureLevels.begin(), s_featureLevels.end(),
|
||||
[&] (const std::pair<std::string, D3D_FEATURE_LEVEL>& pair) {
|
||||
return pair.first == maxLevel;
|
||||
});
|
||||
|
||||
if (entry != s_featureLevels.end())
|
||||
return entry->second;
|
||||
|
||||
// Otherwise, check the actually available device features
|
||||
return D3D11DeviceFeatures::GetMaxFeatureLevel(Instance, Adapter);
|
||||
}
|
||||
|
||||
|
||||
DxvkDeviceFeatures D3D11Device::GetDeviceFeatures(
|
||||
const Rc<DxvkAdapter>& adapter,
|
||||
D3D_FEATURE_LEVEL featureLevel) {
|
||||
DxvkDeviceFeatures supported = adapter->features();
|
||||
const Rc<DxvkAdapter>& Adapter) {
|
||||
DxvkDeviceFeatures supported = Adapter->features();
|
||||
DxvkDeviceFeatures enabled = {};
|
||||
|
||||
// Required for feature level 10_1
|
||||
enabled.core.features.depthBiasClamp = VK_TRUE;
|
||||
enabled.core.features.depthClamp = VK_TRUE;
|
||||
enabled.core.features.dualSrcBlend = VK_TRUE;
|
||||
enabled.core.features.fillModeNonSolid = VK_TRUE;
|
||||
enabled.core.features.fullDrawIndexUint32 = VK_TRUE;
|
||||
enabled.core.features.geometryShader = VK_TRUE;
|
||||
enabled.core.features.robustBufferAccess = VK_TRUE;
|
||||
enabled.core.features.shaderStorageImageWriteWithoutFormat = VK_TRUE;
|
||||
enabled.core.features.depthBounds = supported.core.features.depthBounds;
|
||||
enabled.core.features.imageCubeArray = VK_TRUE;
|
||||
enabled.core.features.independentBlend = VK_TRUE;
|
||||
enabled.core.features.multiViewport = VK_TRUE;
|
||||
enabled.core.features.occlusionQueryPrecise = VK_TRUE;
|
||||
enabled.core.features.pipelineStatisticsQuery = supported.core.features.pipelineStatisticsQuery;
|
||||
enabled.core.features.sampleRateShading = VK_TRUE;
|
||||
enabled.core.features.samplerAnisotropy = supported.core.features.samplerAnisotropy;
|
||||
enabled.core.features.shaderClipDistance = VK_TRUE;
|
||||
enabled.core.features.shaderCullDistance = VK_TRUE;
|
||||
enabled.core.features.shaderImageGatherExtended = VK_TRUE;
|
||||
enabled.core.features.textureCompressionBC = VK_TRUE;
|
||||
|
||||
enabled.shaderDrawParameters.shaderDrawParameters = VK_TRUE;
|
||||
enabled.vk11.shaderDrawParameters = VK_TRUE;
|
||||
|
||||
enabled.extMemoryPriority.memoryPriority = supported.extMemoryPriority.memoryPriority;
|
||||
enabled.vk12.samplerMirrorClampToEdge = VK_TRUE;
|
||||
|
||||
enabled.extRobustness2.robustBufferAccess2 = supported.extRobustness2.robustBufferAccess2;
|
||||
enabled.extRobustness2.robustImageAccess2 = supported.extRobustness2.robustImageAccess2;
|
||||
enabled.extRobustness2.nullDescriptor = supported.extRobustness2.nullDescriptor;
|
||||
enabled.vk13.shaderDemoteToHelperInvocation = VK_TRUE;
|
||||
|
||||
enabled.extShaderDemoteToHelperInvocation.shaderDemoteToHelperInvocation = supported.extShaderDemoteToHelperInvocation.shaderDemoteToHelperInvocation;
|
||||
enabled.extCustomBorderColor.customBorderColors = supported.extCustomBorderColor.customBorderColorWithoutFormat;
|
||||
enabled.extCustomBorderColor.customBorderColorWithoutFormat = supported.extCustomBorderColor.customBorderColorWithoutFormat;
|
||||
|
||||
enabled.extTransformFeedback.transformFeedback = VK_TRUE;
|
||||
enabled.extTransformFeedback.geometryStreams = VK_TRUE;
|
||||
|
||||
enabled.extVertexAttributeDivisor.vertexAttributeInstanceRateDivisor = supported.extVertexAttributeDivisor.vertexAttributeInstanceRateDivisor;
|
||||
enabled.extVertexAttributeDivisor.vertexAttributeInstanceRateZeroDivisor = supported.extVertexAttributeDivisor.vertexAttributeInstanceRateZeroDivisor;
|
||||
|
||||
if (supported.extCustomBorderColor.customBorderColorWithoutFormat) {
|
||||
enabled.extCustomBorderColor.customBorderColors = VK_TRUE;
|
||||
enabled.extCustomBorderColor.customBorderColorWithoutFormat = VK_TRUE;
|
||||
}
|
||||
|
||||
if (featureLevel >= D3D_FEATURE_LEVEL_9_1) {
|
||||
enabled.core.features.depthClamp = VK_TRUE;
|
||||
enabled.core.features.depthBiasClamp = VK_TRUE;
|
||||
enabled.core.features.fillModeNonSolid = VK_TRUE;
|
||||
enabled.core.features.pipelineStatisticsQuery = supported.core.features.pipelineStatisticsQuery;
|
||||
enabled.core.features.sampleRateShading = VK_TRUE;
|
||||
enabled.core.features.samplerAnisotropy = supported.core.features.samplerAnisotropy;
|
||||
enabled.core.features.shaderClipDistance = VK_TRUE;
|
||||
enabled.core.features.shaderCullDistance = VK_TRUE;
|
||||
enabled.core.features.textureCompressionBC = VK_TRUE;
|
||||
enabled.extDepthClipEnable.depthClipEnable = supported.extDepthClipEnable.depthClipEnable;
|
||||
enabled.extHostQueryReset.hostQueryReset = VK_TRUE;
|
||||
}
|
||||
|
||||
if (featureLevel >= D3D_FEATURE_LEVEL_9_2) {
|
||||
enabled.core.features.occlusionQueryPrecise = VK_TRUE;
|
||||
}
|
||||
|
||||
if (featureLevel >= D3D_FEATURE_LEVEL_9_3) {
|
||||
enabled.core.features.independentBlend = VK_TRUE;
|
||||
enabled.core.features.multiViewport = VK_TRUE;
|
||||
}
|
||||
|
||||
if (featureLevel >= D3D_FEATURE_LEVEL_10_0) {
|
||||
enabled.core.features.fullDrawIndexUint32 = VK_TRUE;
|
||||
enabled.core.features.logicOp = supported.core.features.logicOp;
|
||||
enabled.core.features.shaderImageGatherExtended = VK_TRUE;
|
||||
enabled.core.features.variableMultisampleRate = supported.core.features.variableMultisampleRate;
|
||||
enabled.extTransformFeedback.transformFeedback = VK_TRUE;
|
||||
enabled.extTransformFeedback.geometryStreams = VK_TRUE;
|
||||
}
|
||||
|
||||
if (featureLevel >= D3D_FEATURE_LEVEL_10_1) {
|
||||
enabled.core.features.dualSrcBlend = VK_TRUE;
|
||||
enabled.core.features.imageCubeArray = VK_TRUE;
|
||||
}
|
||||
|
||||
if (featureLevel >= D3D_FEATURE_LEVEL_11_0) {
|
||||
enabled.core.features.drawIndirectFirstInstance = VK_TRUE;
|
||||
enabled.core.features.fragmentStoresAndAtomics = VK_TRUE;
|
||||
enabled.core.features.multiDrawIndirect = VK_TRUE;
|
||||
enabled.core.features.shaderFloat64 = supported.core.features.shaderFloat64;
|
||||
enabled.core.features.shaderInt64 = supported.core.features.shaderInt64;
|
||||
enabled.core.features.shaderStorageImageReadWithoutFormat = supported.core.features.shaderStorageImageReadWithoutFormat;
|
||||
enabled.core.features.tessellationShader = VK_TRUE;
|
||||
}
|
||||
|
||||
if (featureLevel >= D3D_FEATURE_LEVEL_11_1) {
|
||||
enabled.core.features.logicOp = VK_TRUE;
|
||||
enabled.core.features.variableMultisampleRate = VK_TRUE;
|
||||
enabled.core.features.vertexPipelineStoresAndAtomics = VK_TRUE;
|
||||
}
|
||||
|
||||
// Required for Feature Level 11_0
|
||||
enabled.core.features.drawIndirectFirstInstance = supported.core.features.drawIndirectFirstInstance;
|
||||
enabled.core.features.fragmentStoresAndAtomics = supported.core.features.fragmentStoresAndAtomics;
|
||||
enabled.core.features.multiDrawIndirect = supported.core.features.multiDrawIndirect;
|
||||
enabled.core.features.tessellationShader = supported.core.features.tessellationShader;
|
||||
|
||||
// Required for Feature Level 11_1
|
||||
enabled.core.features.logicOp = supported.core.features.logicOp;
|
||||
enabled.core.features.vertexPipelineStoresAndAtomics = supported.core.features.vertexPipelineStoresAndAtomics;
|
||||
|
||||
// Required for Feature Level 12_0
|
||||
enabled.core.features.sparseBinding = supported.core.features.sparseBinding;
|
||||
enabled.core.features.sparseResidencyBuffer = supported.core.features.sparseResidencyBuffer;
|
||||
enabled.core.features.sparseResidencyImage2D = supported.core.features.sparseResidencyImage2D;
|
||||
enabled.core.features.sparseResidencyImage3D = supported.core.features.sparseResidencyImage3D;
|
||||
enabled.core.features.sparseResidency2Samples = supported.core.features.sparseResidency2Samples;
|
||||
enabled.core.features.sparseResidency4Samples = supported.core.features.sparseResidency4Samples;
|
||||
enabled.core.features.sparseResidency8Samples = supported.core.features.sparseResidency8Samples;
|
||||
enabled.core.features.sparseResidency16Samples = supported.core.features.sparseResidency16Samples;
|
||||
enabled.core.features.sparseResidencyAliased = supported.core.features.sparseResidencyAliased;
|
||||
enabled.core.features.shaderResourceResidency = supported.core.features.shaderResourceResidency;
|
||||
enabled.core.features.shaderResourceMinLod = supported.core.features.shaderResourceMinLod;
|
||||
enabled.vk12.samplerFilterMinmax = supported.vk12.samplerFilterMinmax;
|
||||
|
||||
// Required for Feature Level 12_1
|
||||
enabled.extFragmentShaderInterlock.fragmentShaderSampleInterlock = supported.extFragmentShaderInterlock.fragmentShaderSampleInterlock;
|
||||
enabled.extFragmentShaderInterlock.fragmentShaderPixelInterlock = supported.extFragmentShaderInterlock.fragmentShaderPixelInterlock;
|
||||
|
||||
// Optional in any feature level
|
||||
enabled.core.features.depthBounds = supported.core.features.depthBounds;
|
||||
enabled.core.features.shaderFloat64 = supported.core.features.shaderFloat64;
|
||||
enabled.core.features.shaderInt64 = supported.core.features.shaderInt64;
|
||||
|
||||
// Depth bias control
|
||||
enabled.extDepthBiasControl.depthBiasControl = supported.extDepthBiasControl.depthBiasControl;
|
||||
enabled.extDepthBiasControl.depthBiasExact = supported.extDepthBiasControl.depthBiasExact;
|
||||
enabled.extDepthBiasControl.leastRepresentableValueForceUnormRepresentation = supported.extDepthBiasControl.leastRepresentableValueForceUnormRepresentation;
|
||||
|
||||
return enabled;
|
||||
}
|
||||
|
||||
@ -2022,11 +1984,20 @@ namespace dxvk {
|
||||
auto shader = commonShader.GetShader();
|
||||
|
||||
if (shader->flags().test(DxvkShaderFlag::ExportsStencilRef)
|
||||
&& !m_dxvkDevice->extensions().extShaderStencilExport)
|
||||
&& !m_dxvkDevice->features().extShaderStencilExport)
|
||||
return E_INVALIDARG;
|
||||
|
||||
if (shader->flags().test(DxvkShaderFlag::ExportsViewportIndexLayerFromVertexStage)
|
||||
&& !m_dxvkDevice->extensions().extShaderViewportIndexLayer)
|
||||
&& (!m_dxvkDevice->features().vk12.shaderOutputViewportIndex
|
||||
|| !m_dxvkDevice->features().vk12.shaderOutputLayer))
|
||||
return E_INVALIDARG;
|
||||
|
||||
if (shader->flags().test(DxvkShaderFlag::UsesSparseResidency)
|
||||
&& !m_dxvkDevice->features().core.features.shaderResourceResidency)
|
||||
return E_INVALIDARG;
|
||||
|
||||
if (shader->flags().test(DxvkShaderFlag::UsesFragmentCoverage)
|
||||
&& !m_dxvkDevice->properties().extConservativeRasterization.fullyCoveredFragmentShaderInputVariable)
|
||||
return E_INVALIDARG;
|
||||
|
||||
*pShaderModule = std::move(commonShader);
|
||||
@ -2042,33 +2013,33 @@ namespace dxvk {
|
||||
if (pFlags2 != nullptr) *pFlags2 = 0;
|
||||
|
||||
// Unsupported or invalid format
|
||||
if (Format != DXGI_FORMAT_UNKNOWN && fmtMapping.Format == VK_FORMAT_UNDEFINED)
|
||||
if (Format && fmtMapping.Format == VK_FORMAT_UNDEFINED)
|
||||
return E_FAIL;
|
||||
|
||||
// Query Vulkan format properties and supported features for it
|
||||
const DxvkFormatInfo* fmtProperties = imageFormatInfo(fmtMapping.Format);
|
||||
const DxvkFormatInfo* fmtProperties = lookupFormatInfo(fmtMapping.Format);
|
||||
|
||||
VkFormatProperties fmtSupport = fmtMapping.Format != VK_FORMAT_UNDEFINED
|
||||
? m_dxvkAdapter->formatProperties(fmtMapping.Format)
|
||||
: VkFormatProperties();
|
||||
DxvkFormatFeatures fmtSupport = fmtMapping.Format != VK_FORMAT_UNDEFINED
|
||||
? m_dxvkDevice->getFormatFeatures(fmtMapping.Format)
|
||||
: DxvkFormatFeatures();
|
||||
|
||||
VkFormatFeatureFlags bufFeatures = fmtSupport.bufferFeatures;
|
||||
VkFormatFeatureFlags imgFeatures = fmtSupport.optimalTilingFeatures | fmtSupport.linearTilingFeatures;
|
||||
VkFormatFeatureFlags2 bufFeatures = fmtSupport.buffer;
|
||||
VkFormatFeatureFlags2 imgFeatures = fmtSupport.optimal | fmtSupport.linear;
|
||||
|
||||
// For multi-plane images, we want to check available view formats as well
|
||||
if (fmtProperties->flags.test(DxvkFormatFlag::MultiPlane)) {
|
||||
const VkFormatFeatureFlags featureMask
|
||||
= VK_FORMAT_FEATURE_SAMPLED_IMAGE_BIT
|
||||
| VK_FORMAT_FEATURE_STORAGE_IMAGE_BIT
|
||||
| VK_FORMAT_FEATURE_COLOR_ATTACHMENT_BIT
|
||||
| VK_FORMAT_FEATURE_COLOR_ATTACHMENT_BLEND_BIT
|
||||
| VK_FORMAT_FEATURE_SAMPLED_IMAGE_FILTER_LINEAR_BIT;
|
||||
const VkFormatFeatureFlags2 featureMask
|
||||
= VK_FORMAT_FEATURE_2_SAMPLED_IMAGE_BIT
|
||||
| VK_FORMAT_FEATURE_2_STORAGE_IMAGE_BIT
|
||||
| VK_FORMAT_FEATURE_2_COLOR_ATTACHMENT_BIT
|
||||
| VK_FORMAT_FEATURE_2_COLOR_ATTACHMENT_BLEND_BIT
|
||||
| VK_FORMAT_FEATURE_2_SAMPLED_IMAGE_FILTER_LINEAR_BIT;
|
||||
|
||||
DXGI_VK_FORMAT_FAMILY formatFamily = LookupFamily(Format, DXGI_VK_FORMAT_MODE_ANY);
|
||||
|
||||
for (uint32_t i = 0; i < formatFamily.FormatCount; i++) {
|
||||
VkFormatProperties viewFmtSupport = m_dxvkAdapter->formatProperties(formatFamily.Formats[i]);
|
||||
imgFeatures |= (viewFmtSupport.optimalTilingFeatures | viewFmtSupport.linearTilingFeatures) & featureMask;
|
||||
DxvkFormatFeatures viewFmtSupport = m_dxvkDevice->getFormatFeatures(formatFamily.Formats[i]);
|
||||
imgFeatures |= (viewFmtSupport.optimal | viewFmtSupport.linear) & featureMask;
|
||||
}
|
||||
}
|
||||
|
||||
@ -2076,12 +2047,11 @@ namespace dxvk {
|
||||
UINT flags2 = 0;
|
||||
|
||||
// Format can be used for shader resource views with buffers
|
||||
if (bufFeatures & VK_FORMAT_FEATURE_UNIFORM_TEXEL_BUFFER_BIT
|
||||
|| Format == DXGI_FORMAT_UNKNOWN)
|
||||
if ((bufFeatures & VK_FORMAT_FEATURE_2_UNIFORM_TEXEL_BUFFER_BIT) || !Format)
|
||||
flags1 |= D3D11_FORMAT_SUPPORT_BUFFER;
|
||||
|
||||
// Format can be used for vertex data
|
||||
if (bufFeatures & VK_FORMAT_FEATURE_VERTEX_BUFFER_BIT)
|
||||
if (bufFeatures & VK_FORMAT_FEATURE_2_VERTEX_BUFFER_BIT)
|
||||
flags1 |= D3D11_FORMAT_SUPPORT_IA_VERTEX_BUFFER;
|
||||
|
||||
// Format can be used for index data. Only
|
||||
@ -2107,19 +2077,31 @@ namespace dxvk {
|
||||
|| Format == DXGI_FORMAT_R32G32B32A32_SINT)
|
||||
flags1 |= D3D11_FORMAT_SUPPORT_SO_BUFFER;
|
||||
|
||||
if (imgFeatures & VK_FORMAT_FEATURE_SAMPLED_IMAGE_BIT
|
||||
|| imgFeatures & VK_FORMAT_FEATURE_STORAGE_IMAGE_BIT) {
|
||||
if (imgFeatures & (VK_FORMAT_FEATURE_2_SAMPLED_IMAGE_BIT | VK_FORMAT_FEATURE_2_STORAGE_IMAGE_BIT)) {
|
||||
const VkFormat depthFormat = LookupFormat(Format, DXGI_VK_FORMAT_MODE_DEPTH).Format;
|
||||
|
||||
if (GetImageTypeSupport(fmtMapping.Format, VK_IMAGE_TYPE_1D)) flags1 |= D3D11_FORMAT_SUPPORT_TEXTURE1D;
|
||||
if (GetImageTypeSupport(fmtMapping.Format, VK_IMAGE_TYPE_2D)) flags1 |= D3D11_FORMAT_SUPPORT_TEXTURE2D;
|
||||
if (GetImageTypeSupport(fmtMapping.Format, VK_IMAGE_TYPE_3D)) flags1 |= D3D11_FORMAT_SUPPORT_TEXTURE3D;
|
||||
|
||||
if (GetImageTypeSupport(fmtMapping.Format, VK_IMAGE_TYPE_1D, 0)) flags1 |= D3D11_FORMAT_SUPPORT_TEXTURE1D;
|
||||
if (GetImageTypeSupport(fmtMapping.Format, VK_IMAGE_TYPE_2D, 0)) flags1 |= D3D11_FORMAT_SUPPORT_TEXTURE2D;
|
||||
if (GetImageTypeSupport(fmtMapping.Format, VK_IMAGE_TYPE_3D, 0)) flags1 |= D3D11_FORMAT_SUPPORT_TEXTURE3D;
|
||||
|
||||
// We only support tiled resources with a single aspect
|
||||
D3D11_TILED_RESOURCES_TIER tiledResourcesTier = m_deviceFeatures.GetTiledResourcesTier();
|
||||
VkImageAspectFlags sparseAspects = VK_IMAGE_ASPECT_COLOR_BIT | VK_IMAGE_ASPECT_DEPTH_BIT;
|
||||
|
||||
if (tiledResourcesTier && !(fmtProperties->aspectMask & ~sparseAspects)) {
|
||||
VkImageCreateFlags flags = VK_IMAGE_CREATE_SPARSE_BINDING_BIT
|
||||
| VK_IMAGE_CREATE_SPARSE_RESIDENCY_BIT
|
||||
| VK_IMAGE_CREATE_SPARSE_ALIASED_BIT;
|
||||
|
||||
if (GetImageTypeSupport(fmtMapping.Format, VK_IMAGE_TYPE_2D, flags))
|
||||
flags2 |= D3D11_FORMAT_SUPPORT2_TILED;
|
||||
}
|
||||
|
||||
flags1 |= D3D11_FORMAT_SUPPORT_MIP
|
||||
| D3D11_FORMAT_SUPPORT_CAST_WITHIN_BIT_LAYOUT;
|
||||
|
||||
|
||||
// Format can be read
|
||||
if (imgFeatures & VK_FORMAT_FEATURE_SAMPLED_IMAGE_BIT) {
|
||||
if (imgFeatures & VK_FORMAT_FEATURE_2_SAMPLED_IMAGE_BIT) {
|
||||
flags1 |= D3D11_FORMAT_SUPPORT_TEXTURECUBE
|
||||
| D3D11_FORMAT_SUPPORT_SHADER_LOAD
|
||||
| D3D11_FORMAT_SUPPORT_SHADER_GATHER
|
||||
@ -2133,7 +2115,7 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
// Format is a color format that can be used for rendering
|
||||
if (imgFeatures & VK_FORMAT_FEATURE_COLOR_ATTACHMENT_BIT) {
|
||||
if (imgFeatures & VK_FORMAT_FEATURE_2_COLOR_ATTACHMENT_BIT) {
|
||||
flags1 |= D3D11_FORMAT_SUPPORT_RENDER_TARGET
|
||||
| D3D11_FORMAT_SUPPORT_MIP_AUTOGEN
|
||||
| D3D11_FORMAT_SUPPORT_VIDEO_PROCESSOR_OUTPUT;
|
||||
@ -2143,14 +2125,14 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
// Format supports blending when used for rendering
|
||||
if (imgFeatures & VK_FORMAT_FEATURE_COLOR_ATTACHMENT_BLEND_BIT)
|
||||
if (imgFeatures & VK_FORMAT_FEATURE_2_COLOR_ATTACHMENT_BLEND_BIT)
|
||||
flags1 |= D3D11_FORMAT_SUPPORT_BLENDABLE;
|
||||
|
||||
// Format is a depth-stencil format that can be used for rendering
|
||||
if (imgFeatures & VK_FORMAT_FEATURE_DEPTH_STENCIL_ATTACHMENT_BIT)
|
||||
if (imgFeatures & VK_FORMAT_FEATURE_2_DEPTH_STENCIL_ATTACHMENT_BIT)
|
||||
flags1 |= D3D11_FORMAT_SUPPORT_DEPTH_STENCIL;
|
||||
|
||||
// FIXME implement properly. This would require a VkSurface.
|
||||
// Report supported swap chain formats
|
||||
if (Format == DXGI_FORMAT_R8G8B8A8_UNORM
|
||||
|| Format == DXGI_FORMAT_R8G8B8A8_UNORM_SRGB
|
||||
|| Format == DXGI_FORMAT_B8G8R8A8_UNORM
|
||||
@ -2161,36 +2143,61 @@ namespace dxvk {
|
||||
flags1 |= D3D11_FORMAT_SUPPORT_DISPLAY;
|
||||
|
||||
// Query multisample support for this format
|
||||
VkImageFormatProperties imgFmtProperties;
|
||||
|
||||
VkResult status = m_dxvkAdapter->imageFormatProperties(fmtMapping.Format,
|
||||
VK_IMAGE_TYPE_2D, VK_IMAGE_TILING_OPTIMAL,
|
||||
(fmtProperties->aspectMask & VK_IMAGE_ASPECT_COLOR_BIT)
|
||||
? VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT
|
||||
: VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT,
|
||||
0, imgFmtProperties);
|
||||
|
||||
if (status == VK_SUCCESS && imgFmtProperties.sampleCounts > VK_SAMPLE_COUNT_1_BIT) {
|
||||
VkImageUsageFlags usage = (fmtProperties->aspectMask & VK_IMAGE_ASPECT_COLOR_BIT)
|
||||
? VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT
|
||||
: VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT;
|
||||
|
||||
DxvkFormatQuery formatQuery = { };
|
||||
formatQuery.format = fmtMapping.Format;
|
||||
formatQuery.type = VK_IMAGE_TYPE_2D;
|
||||
formatQuery.tiling = VK_IMAGE_TILING_OPTIMAL;
|
||||
formatQuery.usage = usage;
|
||||
|
||||
auto limits = m_dxvkDevice->getFormatLimits(formatQuery);
|
||||
|
||||
if (limits && limits->sampleCounts > VK_SAMPLE_COUNT_1_BIT) {
|
||||
flags1 |= D3D11_FORMAT_SUPPORT_MULTISAMPLE_RENDERTARGET
|
||||
| D3D11_FORMAT_SUPPORT_MULTISAMPLE_RESOLVE
|
||||
| D3D11_FORMAT_SUPPORT_MULTISAMPLE_LOAD;
|
||||
}
|
||||
|
||||
// Query whether the format is shareable
|
||||
if ((fmtProperties->aspectMask & (VK_IMAGE_ASPECT_COLOR_BIT | VK_IMAGE_ASPECT_PLANE_0_BIT))
|
||||
&& (m_dxvkDevice->features().khrExternalMemoryWin32)) {
|
||||
constexpr VkExternalMemoryFeatureFlags featureMask
|
||||
= VK_EXTERNAL_MEMORY_FEATURE_EXPORTABLE_BIT
|
||||
| VK_EXTERNAL_MEMORY_FEATURE_IMPORTABLE_BIT;
|
||||
|
||||
formatQuery.handleType = VK_EXTERNAL_MEMORY_HANDLE_TYPE_OPAQUE_WIN32_KMT_BIT;
|
||||
limits = m_dxvkDevice->getFormatLimits(formatQuery);
|
||||
|
||||
if (limits && (limits->externalFeatures & featureMask))
|
||||
flags2 |= D3D11_FORMAT_SUPPORT2_SHAREABLE;
|
||||
}
|
||||
}
|
||||
|
||||
// Format can be used for storage images or storage texel buffers
|
||||
if ((bufFeatures & VK_FORMAT_FEATURE_STORAGE_TEXEL_BUFFER_BIT)
|
||||
&& (imgFeatures & VK_FORMAT_FEATURE_STORAGE_IMAGE_BIT)) {
|
||||
if ((bufFeatures & VK_FORMAT_FEATURE_2_STORAGE_TEXEL_BUFFER_BIT)
|
||||
&& (imgFeatures & VK_FORMAT_FEATURE_2_STORAGE_IMAGE_BIT)
|
||||
&& (imgFeatures & VK_FORMAT_FEATURE_2_STORAGE_WRITE_WITHOUT_FORMAT_BIT)) {
|
||||
flags1 |= D3D11_FORMAT_SUPPORT_TYPED_UNORDERED_ACCESS_VIEW;
|
||||
flags2 |= D3D11_FORMAT_SUPPORT2_UAV_TYPED_STORE;
|
||||
|
||||
if (m_dxvkDevice->features().core.features.shaderStorageImageReadWithoutFormat
|
||||
|| Format == DXGI_FORMAT_R32_UINT
|
||||
|| Format == DXGI_FORMAT_R32_SINT
|
||||
|| Format == DXGI_FORMAT_R32_FLOAT)
|
||||
flags2 |= D3D11_FORMAT_SUPPORT2_UAV_TYPED_LOAD;
|
||||
if (m_dxbcOptions.supportsTypedUavLoadR32) {
|
||||
// If the R32 formats are supported without format declarations,
|
||||
// we can optionally support additional formats for typed loads
|
||||
if (imgFeatures & VK_FORMAT_FEATURE_2_STORAGE_READ_WITHOUT_FORMAT_BIT)
|
||||
flags2 |= D3D11_FORMAT_SUPPORT2_UAV_TYPED_LOAD;
|
||||
} else {
|
||||
// Otherwise, we need to emit format declarations, so we can
|
||||
// only support the basic set of R32 formats for typed loads
|
||||
if (Format == DXGI_FORMAT_R32_FLOAT
|
||||
|| Format == DXGI_FORMAT_R32_UINT
|
||||
|| Format == DXGI_FORMAT_R32_SINT)
|
||||
flags2 |= D3D11_FORMAT_SUPPORT2_UAV_TYPED_LOAD;
|
||||
}
|
||||
|
||||
if (Format == DXGI_FORMAT_R32_UINT
|
||||
|| Format == DXGI_FORMAT_R32_SINT) {
|
||||
if (Format == DXGI_FORMAT_R32_UINT || Format == DXGI_FORMAT_R32_SINT) {
|
||||
flags2 |= D3D11_FORMAT_SUPPORT2_UAV_ATOMIC_ADD
|
||||
| D3D11_FORMAT_SUPPORT2_UAV_ATOMIC_BITWISE_OPS
|
||||
| D3D11_FORMAT_SUPPORT2_UAV_ATOMIC_COMPARE_STORE_OR_COMPARE_EXCHANGE
|
||||
@ -2215,20 +2222,22 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
BOOL D3D11Device::GetImageTypeSupport(VkFormat Format, VkImageType Type) const {
|
||||
VkImageFormatProperties props;
|
||||
|
||||
VkResult status = m_dxvkAdapter->imageFormatProperties(
|
||||
Format, Type, VK_IMAGE_TILING_OPTIMAL,
|
||||
VK_IMAGE_USAGE_SAMPLED_BIT, 0, props);
|
||||
|
||||
if (status != VK_SUCCESS) {
|
||||
status = m_dxvkAdapter->imageFormatProperties(
|
||||
Format, Type, VK_IMAGE_TILING_LINEAR,
|
||||
VK_IMAGE_USAGE_SAMPLED_BIT, 0, props);
|
||||
BOOL D3D11Device::GetImageTypeSupport(VkFormat Format, VkImageType Type, VkImageCreateFlags Flags) const {
|
||||
DxvkFormatQuery formatQuery = { };
|
||||
formatQuery.format = Format;
|
||||
formatQuery.type = Type;
|
||||
formatQuery.tiling = VK_IMAGE_TILING_OPTIMAL;
|
||||
formatQuery.usage = VK_IMAGE_USAGE_SAMPLED_BIT;
|
||||
formatQuery.flags = Flags;
|
||||
|
||||
auto properties = m_dxvkDevice->getFormatLimits(formatQuery);
|
||||
|
||||
if (!properties) {
|
||||
formatQuery.tiling = VK_IMAGE_TILING_LINEAR;
|
||||
properties = m_dxvkDevice->getFormatLimits(formatQuery);
|
||||
}
|
||||
|
||||
return status == VK_SUCCESS;
|
||||
|
||||
return properties.has_value();
|
||||
}
|
||||
|
||||
|
||||
@ -2268,6 +2277,7 @@ namespace dxvk {
|
||||
if (ppResource == nullptr)
|
||||
return S_FALSE;
|
||||
|
||||
#ifdef _WIN32
|
||||
HANDLE ntHandle = IsKmtHandle ? openKmtHandle(hResource) : hResource;
|
||||
|
||||
if (ntHandle == INVALID_HANDLE_VALUE) {
|
||||
@ -2299,10 +2309,14 @@ namespace dxvk {
|
||||
d3d11Desc.CPUAccessFlags = metadata.CPUAccessFlags;
|
||||
d3d11Desc.MiscFlags = metadata.MiscFlags;
|
||||
d3d11Desc.TextureLayout = metadata.TextureLayout;
|
||||
if ((d3d11Desc.MiscFlags & D3D11_RESOURCE_MISC_SHARED_NTHANDLE) && !(d3d11Desc.MiscFlags & (D3D11_RESOURCE_MISC_SHARED | D3D11_RESOURCE_MISC_SHARED_KEYEDMUTEX))) {
|
||||
Logger::warn("Fixing up wrong MiscFlags");
|
||||
d3d11Desc.MiscFlags |= D3D11_RESOURCE_MISC_SHARED;
|
||||
}
|
||||
|
||||
// Only 2D textures may be shared
|
||||
try {
|
||||
const Com<D3D11Texture2D> texture = new D3D11Texture2D(this, &d3d11Desc, hResource);
|
||||
const Com<D3D11Texture2D> texture = new D3D11Texture2D(this, &d3d11Desc, nullptr, hResource);
|
||||
texture->QueryInterface(ReturnedInterface, ppResource);
|
||||
return S_OK;
|
||||
}
|
||||
@ -2310,6 +2324,10 @@ namespace dxvk {
|
||||
Logger::err(e.message());
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
#else
|
||||
Logger::warn("D3D11Device::OpenSharedResourceGeneric: Not supported on this platform.");
|
||||
return E_INVALIDARG;
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
@ -2318,36 +2336,16 @@ namespace dxvk {
|
||||
Void* pData,
|
||||
UINT RowPitch,
|
||||
UINT DepthPitch,
|
||||
ID3D11Resource* pResource,
|
||||
D3D11CommonTexture* pTexture,
|
||||
UINT Subresource,
|
||||
const D3D11_BOX* pBox) {
|
||||
auto texture = GetCommonTexture(pResource);
|
||||
|
||||
if (!texture)
|
||||
return;
|
||||
|
||||
// Validate texture state and skip invalid calls
|
||||
if (texture->Desc()->Usage != D3D11_USAGE_DEFAULT
|
||||
|| texture->GetMapMode() == D3D11_COMMON_TEXTURE_MAP_MODE_NONE
|
||||
|| texture->CountSubresources() <= Subresource
|
||||
|| texture->GetMapType(Subresource) == D3D11_MAP(~0u))
|
||||
return;
|
||||
|
||||
// Retrieve image format information
|
||||
VkFormat packedFormat = LookupPackedFormat(
|
||||
texture->Desc()->Format,
|
||||
texture->GetFormatMode()).Format;
|
||||
|
||||
auto formatInfo = imageFormatInfo(packedFormat);
|
||||
|
||||
// Validate box against subresource dimensions
|
||||
Rc<DxvkImage> image = texture->GetImage();
|
||||
|
||||
auto subresource = texture->GetSubresourceFromIndex(
|
||||
auto formatInfo = lookupFormatInfo(pTexture->GetPackedFormat());
|
||||
auto subresource = pTexture->GetSubresourceFromIndex(
|
||||
formatInfo->aspectMask, Subresource);
|
||||
|
||||
|
||||
VkOffset3D offset = { 0, 0, 0 };
|
||||
VkExtent3D extent = image->mipLevelExtent(subresource.mipLevel);
|
||||
VkExtent3D extent = pTexture->MipLevelExtent(subresource.mipLevel);
|
||||
|
||||
if (pBox) {
|
||||
if (pBox->left >= pBox->right
|
||||
@ -2371,88 +2369,55 @@ namespace dxvk {
|
||||
pBox->back - pBox->front };
|
||||
}
|
||||
|
||||
// We can only operate on full blocks of compressed images
|
||||
offset = util::computeBlockOffset(offset, formatInfo->blockSize);
|
||||
extent = util::computeBlockCount(extent, formatInfo->blockSize);
|
||||
// Copy image data, one plane at a time for multi-plane formats
|
||||
Rc<DxvkImage> image = pTexture->GetImage();
|
||||
VkDeviceSize dataOffset = 0;
|
||||
|
||||
// Determine the memory layout of the image data
|
||||
D3D11_MAPPED_SUBRESOURCE subresourceData = { };
|
||||
for (uint32_t i = 0; i < pTexture->GetPlaneCount(); i++) {
|
||||
// Find current image aspects to process
|
||||
VkImageAspectFlags aspect = formatInfo->aspectMask;
|
||||
|
||||
if (texture->GetMapMode() == D3D11_COMMON_TEXTURE_MAP_MODE_DIRECT) {
|
||||
VkSubresourceLayout layout = image->querySubresourceLayout(subresource);
|
||||
subresourceData.pData = image->mapPtr(layout.offset);
|
||||
subresourceData.RowPitch = layout.rowPitch;
|
||||
subresourceData.DepthPitch = layout.depthPitch;
|
||||
} else {
|
||||
subresourceData.pData = texture->GetMappedBuffer(Subresource)->mapPtr(0);
|
||||
subresourceData.RowPitch = formatInfo->elementSize * extent.width;
|
||||
subresourceData.DepthPitch = formatInfo->elementSize * extent.width * extent.height;
|
||||
if (formatInfo->flags.test(DxvkFormatFlag::MultiPlane))
|
||||
aspect = vk::getPlaneAspect(i);
|
||||
|
||||
// Compute data layout of the current subresource
|
||||
D3D11_COMMON_TEXTURE_SUBRESOURCE_LAYOUT layout = pTexture->GetSubresourceLayout(aspect, Subresource);
|
||||
|
||||
// Compute actual map pointer, accounting for the region offset
|
||||
VkDeviceSize mapOffset = pTexture->ComputeMappedOffset(Subresource, i, offset);
|
||||
|
||||
void* mapPtr = pTexture->GetMapMode() == D3D11_COMMON_TEXTURE_MAP_MODE_BUFFER
|
||||
? pTexture->GetMappedBuffer(Subresource)->mapPtr(mapOffset)
|
||||
: image->mapPtr(mapOffset);
|
||||
|
||||
if constexpr (std::is_const<Void>::value) {
|
||||
// WriteToSubresource
|
||||
auto srcData = reinterpret_cast<const char*>(pData) + dataOffset;
|
||||
|
||||
util::packImageData(mapPtr, srcData, RowPitch, DepthPitch,
|
||||
layout.RowPitch, layout.DepthPitch, image->info().type,
|
||||
extent, 1, formatInfo, aspect);
|
||||
} else {
|
||||
// ReadFromSubresource
|
||||
auto dstData = reinterpret_cast<char*>(pData) + dataOffset;
|
||||
|
||||
util::packImageData(dstData, mapPtr,
|
||||
layout.RowPitch, layout.DepthPitch,
|
||||
RowPitch, DepthPitch, image->info().type,
|
||||
extent, 1, formatInfo, aspect);
|
||||
}
|
||||
|
||||
// Advance linear data pointer by the size of the current aspect
|
||||
dataOffset += util::computeImageDataSize(
|
||||
pTexture->GetPackedFormat(), extent, aspect);
|
||||
}
|
||||
|
||||
if constexpr (std::is_const<Void>::value) {
|
||||
// WriteToSubresource
|
||||
auto src = reinterpret_cast<const char*>(pData);
|
||||
auto dst = reinterpret_cast< char*>(subresourceData.pData);
|
||||
|
||||
for (uint32_t z = 0; z < extent.depth; z++) {
|
||||
for (uint32_t y = 0; y < extent.height; y++) {
|
||||
std::memcpy(
|
||||
dst + (offset.z + z) * subresourceData.DepthPitch
|
||||
+ (offset.y + y) * subresourceData.RowPitch
|
||||
+ (offset.x) * formatInfo->elementSize,
|
||||
src + z * DepthPitch
|
||||
+ y * RowPitch,
|
||||
formatInfo->elementSize * extent.width);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
// ReadFromSubresource
|
||||
auto src = reinterpret_cast<const char*>(subresourceData.pData);
|
||||
auto dst = reinterpret_cast< char*>(pData);
|
||||
|
||||
for (uint32_t z = 0; z < extent.depth; z++) {
|
||||
for (uint32_t y = 0; y < extent.height; y++) {
|
||||
std::memcpy(
|
||||
dst + z * DepthPitch
|
||||
+ y * RowPitch,
|
||||
src + (offset.z + z) * subresourceData.DepthPitch
|
||||
+ (offset.y + y) * subresourceData.RowPitch
|
||||
+ (offset.x) * formatInfo->elementSize,
|
||||
formatInfo->elementSize * extent.width);
|
||||
}
|
||||
}
|
||||
}
|
||||
// Track dirty texture region if necessary
|
||||
if constexpr (std::is_const<Void>::value)
|
||||
pTexture->AddDirtyRegion(Subresource, offset, extent);
|
||||
}
|
||||
|
||||
|
||||
D3D_FEATURE_LEVEL D3D11Device::GetMaxFeatureLevel(const Rc<DxvkInstance>& pInstance) {
|
||||
static const std::array<std::pair<std::string, D3D_FEATURE_LEVEL>, 9> s_featureLevels = {{
|
||||
{ "12_1", D3D_FEATURE_LEVEL_12_1 },
|
||||
{ "12_0", D3D_FEATURE_LEVEL_12_0 },
|
||||
{ "11_1", D3D_FEATURE_LEVEL_11_1 },
|
||||
{ "11_0", D3D_FEATURE_LEVEL_11_0 },
|
||||
{ "10_1", D3D_FEATURE_LEVEL_10_1 },
|
||||
{ "10_0", D3D_FEATURE_LEVEL_10_0 },
|
||||
{ "9_3", D3D_FEATURE_LEVEL_9_3 },
|
||||
{ "9_2", D3D_FEATURE_LEVEL_9_2 },
|
||||
{ "9_1", D3D_FEATURE_LEVEL_9_1 },
|
||||
}};
|
||||
|
||||
const std::string maxLevel = pInstance->config()
|
||||
.getOption<std::string>("d3d11.maxFeatureLevel");
|
||||
|
||||
auto entry = std::find_if(s_featureLevels.begin(), s_featureLevels.end(),
|
||||
[&] (const std::pair<std::string, D3D_FEATURE_LEVEL>& pair) {
|
||||
return pair.first == maxLevel;
|
||||
});
|
||||
|
||||
return entry != s_featureLevels.end()
|
||||
? entry->second
|
||||
: D3D_FEATURE_LEVEL_11_1;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
D3D11DeviceExt::D3D11DeviceExt(
|
||||
D3D11DXGIDevice* pContainer,
|
||||
@ -2482,7 +2447,6 @@ namespace dxvk {
|
||||
BOOL STDMETHODCALLTYPE D3D11DeviceExt::GetExtensionSupport(
|
||||
D3D11_VK_EXTENSION Extension) {
|
||||
const auto& deviceFeatures = m_device->GetDXVKDevice()->features();
|
||||
const auto& deviceExtensions = m_device->GetDXVKDevice()->extensions();
|
||||
|
||||
switch (Extension) {
|
||||
case D3D11_VK_EXT_BARRIER_CONTROL:
|
||||
@ -2493,17 +2457,17 @@ namespace dxvk {
|
||||
|
||||
case D3D11_VK_EXT_MULTI_DRAW_INDIRECT_COUNT:
|
||||
return deviceFeatures.core.features.multiDrawIndirect
|
||||
&& deviceExtensions.khrDrawIndirectCount;
|
||||
&& deviceFeatures.vk12.drawIndirectCount;
|
||||
|
||||
case D3D11_VK_EXT_DEPTH_BOUNDS:
|
||||
return deviceFeatures.core.features.depthBounds;
|
||||
|
||||
case D3D11_VK_NVX_IMAGE_VIEW_HANDLE:
|
||||
return deviceExtensions.nvxImageViewHandle;
|
||||
return deviceFeatures.nvxImageViewHandle;
|
||||
|
||||
case D3D11_VK_NVX_BINARY_IMPORT:
|
||||
return deviceExtensions.nvxBinaryImport
|
||||
&& deviceExtensions.khrBufferDeviceAddress;
|
||||
return deviceFeatures.nvxBinaryImport
|
||||
&& deviceFeatures.vk12.bufferDeviceAddress;
|
||||
|
||||
default:
|
||||
return false;
|
||||
@ -2662,9 +2626,10 @@ namespace dxvk {
|
||||
const DxvkBufferSliceHandle bufSliceHandle = buffer->GetBuffer()->getSliceHandle();
|
||||
VkBuffer vkBuffer = bufSliceHandle.handle;
|
||||
|
||||
VkBufferDeviceAddressInfoKHR bdaInfo = { VK_STRUCTURE_TYPE_BUFFER_DEVICE_ADDRESS_INFO_KHR };
|
||||
VkBufferDeviceAddressInfo bdaInfo = { VK_STRUCTURE_TYPE_BUFFER_DEVICE_ADDRESS_INFO };
|
||||
bdaInfo.buffer = vkBuffer;
|
||||
VkDeviceAddress bufAddr = dxvkDevice->vkd()->vkGetBufferDeviceAddressKHR(vkDevice, &bdaInfo);
|
||||
|
||||
VkDeviceAddress bufAddr = dxvkDevice->vkd()->vkGetBufferDeviceAddress(vkDevice, &bdaInfo);
|
||||
*gpuVAStart = uint64_t(bufAddr) + bufSliceHandle.offset;
|
||||
*gpuVASize = bufSliceHandle.length;
|
||||
}
|
||||
@ -3020,79 +2985,53 @@ namespace dxvk {
|
||||
|
||||
|
||||
|
||||
WineDXGISwapChainFactory::WineDXGISwapChainFactory(
|
||||
DXGIVkSwapChainFactory::DXGIVkSwapChainFactory(
|
||||
D3D11DXGIDevice* pContainer,
|
||||
D3D11Device* pDevice)
|
||||
: m_container(pContainer), m_device(pDevice) {
|
||||
|
||||
}
|
||||
|
||||
|
||||
ULONG STDMETHODCALLTYPE WineDXGISwapChainFactory::AddRef() {
|
||||
|
||||
|
||||
ULONG STDMETHODCALLTYPE DXGIVkSwapChainFactory::AddRef() {
|
||||
return m_device->AddRef();
|
||||
}
|
||||
|
||||
|
||||
ULONG STDMETHODCALLTYPE WineDXGISwapChainFactory::Release() {
|
||||
|
||||
|
||||
ULONG STDMETHODCALLTYPE DXGIVkSwapChainFactory::Release() {
|
||||
return m_device->Release();
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE WineDXGISwapChainFactory::QueryInterface(
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE DXGIVkSwapChainFactory::QueryInterface(
|
||||
REFIID riid,
|
||||
void** ppvObject) {
|
||||
return m_device->QueryInterface(riid, ppvObject);
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE WineDXGISwapChainFactory::CreateSwapChainForHwnd(
|
||||
IDXGIFactory* pFactory,
|
||||
HWND hWnd,
|
||||
const DXGI_SWAP_CHAIN_DESC1* pDesc,
|
||||
const DXGI_SWAP_CHAIN_FULLSCREEN_DESC* pFullscreenDesc,
|
||||
IDXGIOutput* pRestrictToOutput,
|
||||
IDXGISwapChain1** ppSwapChain) {
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE DXGIVkSwapChainFactory::CreateSwapChain(
|
||||
IDXGIVkSurfaceFactory* pSurfaceFactory,
|
||||
const DXGI_SWAP_CHAIN_DESC1* pDesc,
|
||||
IDXGIVkSwapChain** ppSwapChain) {
|
||||
InitReturnPtr(ppSwapChain);
|
||||
|
||||
if (!ppSwapChain || !pDesc || !hWnd)
|
||||
return DXGI_ERROR_INVALID_CALL;
|
||||
|
||||
// Make sure the back buffer size is not zero
|
||||
DXGI_SWAP_CHAIN_DESC1 desc = *pDesc;
|
||||
|
||||
GetWindowClientSize(hWnd,
|
||||
desc.Width ? nullptr : &desc.Width,
|
||||
desc.Height ? nullptr : &desc.Height);
|
||||
|
||||
// If necessary, set up a default set of
|
||||
// fullscreen parameters for the swap chain
|
||||
DXGI_SWAP_CHAIN_FULLSCREEN_DESC fsDesc;
|
||||
|
||||
if (pFullscreenDesc) {
|
||||
fsDesc = *pFullscreenDesc;
|
||||
} else {
|
||||
fsDesc.RefreshRate = { 0, 0 };
|
||||
fsDesc.ScanlineOrdering = DXGI_MODE_SCANLINE_ORDER_UNSPECIFIED;
|
||||
fsDesc.Scaling = DXGI_MODE_SCALING_UNSPECIFIED;
|
||||
fsDesc.Windowed = TRUE;
|
||||
}
|
||||
|
||||
|
||||
try {
|
||||
// Create presenter for the device
|
||||
auto vki = m_device->GetDXVKDevice()->adapter()->vki();
|
||||
|
||||
Com<D3D11SwapChain> presenter = new D3D11SwapChain(
|
||||
m_container, m_device, hWnd, &desc);
|
||||
m_container, m_device, pSurfaceFactory, pDesc);
|
||||
|
||||
// Create the actual swap chain
|
||||
*ppSwapChain = ref(new DxgiSwapChain(
|
||||
pFactory, presenter.ptr(), hWnd, &desc, &fsDesc));
|
||||
*ppSwapChain = presenter.ref();
|
||||
return S_OK;
|
||||
} catch (const DxvkError& e) {
|
||||
Logger::err(e.message());
|
||||
return E_INVALIDARG;
|
||||
return E_FAIL;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
DXGIDXVKDevice::DXGIDXVKDevice(D3D11DXGIDevice* pContainer)
|
||||
: m_container(pContainer), m_apiVersion(11) {
|
||||
@ -3132,26 +3071,30 @@ namespace dxvk {
|
||||
|
||||
D3D11DXGIDevice::D3D11DXGIDevice(
|
||||
IDXGIAdapter* pAdapter,
|
||||
const Rc<DxvkInstance>& pDxvkInstance,
|
||||
const Rc<DxvkAdapter>& pDxvkAdapter,
|
||||
ID3D12Device* pD3D12Device,
|
||||
ID3D12CommandQueue* pD3D12Queue,
|
||||
Rc<DxvkInstance> pDxvkInstance,
|
||||
Rc<DxvkAdapter> pDxvkAdapter,
|
||||
Rc<DxvkDevice> pDxvkDevice,
|
||||
D3D_FEATURE_LEVEL FeatureLevel,
|
||||
UINT FeatureFlags)
|
||||
: m_dxgiAdapter (pAdapter),
|
||||
m_dxvkInstance (pDxvkInstance),
|
||||
m_dxvkAdapter (pDxvkAdapter),
|
||||
m_dxvkDevice (CreateDevice(FeatureLevel)),
|
||||
m_dxvkDevice (pDxvkDevice),
|
||||
m_d3d11Device (this, FeatureLevel, FeatureFlags),
|
||||
m_d3d11DeviceExt(this, &m_d3d11Device),
|
||||
m_d3d11Interop (this, &m_d3d11Device),
|
||||
m_d3d11Video (this, &m_d3d11Device),
|
||||
m_d3d11on12 (this, &m_d3d11Device, pD3D12Device, pD3D12Queue),
|
||||
m_metaDevice (this),
|
||||
m_wineFactory (this, &m_d3d11Device) {
|
||||
m_dxvkFactory (this, &m_d3d11Device) {
|
||||
|
||||
}
|
||||
|
||||
|
||||
D3D11DXGIDevice::~D3D11DXGIDevice() {
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
@ -3205,8 +3148,8 @@ namespace dxvk {
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
if (riid == __uuidof(IWineDXGISwapChainFactory)) {
|
||||
*ppvObject = ref(&m_wineFactory);
|
||||
if (riid == __uuidof(IDXGIVkSwapChainFactory)) {
|
||||
*ppvObject = ref(&m_dxvkFactory);
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
@ -3215,6 +3158,13 @@ namespace dxvk {
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
if (m_d3d11on12.Is11on12Device()) {
|
||||
if (riid == __uuidof(ID3D11On12Device)) {
|
||||
*ppvObject = ref(&m_d3d11on12);
|
||||
return S_OK;
|
||||
}
|
||||
}
|
||||
|
||||
if (riid == __uuidof(ID3D10Multithread)) {
|
||||
Com<ID3D11DeviceContext> context;
|
||||
m_d3d11Device.GetImmediateContext(&context);
|
||||
@ -3228,8 +3178,11 @@ namespace dxvk {
|
||||
if (riid == GUID{0xd56e2a4c,0x5127,0x8437,{0x65,0x8a,0x98,0xc5,0xbb,0x78,0x94,0x98}})
|
||||
return E_NOINTERFACE;
|
||||
|
||||
Logger::warn("D3D11DXGIDevice::QueryInterface: Unknown interface query");
|
||||
Logger::warn(str::format(riid));
|
||||
if (logQueryInterfaceError(__uuidof(IDXGIDXVKDevice), riid)) {
|
||||
Logger::warn("D3D11DXGIDevice::QueryInterface: Unknown interface query");
|
||||
Logger::warn(str::format(riid));
|
||||
}
|
||||
|
||||
return E_NOINTERFACE;
|
||||
}
|
||||
|
||||
@ -3475,10 +3428,4 @@ namespace dxvk {
|
||||
return m_dxvkDevice;
|
||||
}
|
||||
|
||||
|
||||
Rc<DxvkDevice> D3D11DXGIDevice::CreateDevice(D3D_FEATURE_LEVEL FeatureLevel) {
|
||||
DxvkDeviceFeatures deviceFeatures = D3D11Device::GetDeviceFeatures(m_dxvkAdapter, FeatureLevel);
|
||||
return m_dxvkAdapter->createDevice(m_dxvkInstance, deviceFeatures);
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -16,9 +16,11 @@
|
||||
|
||||
#include "d3d11_cmdlist.h"
|
||||
#include "d3d11_cuda.h"
|
||||
#include "d3d11_features.h"
|
||||
#include "d3d11_initializer.h"
|
||||
#include "d3d11_interfaces.h"
|
||||
#include "d3d11_interop.h"
|
||||
#include "d3d11_on_12.h"
|
||||
#include "d3d11_options.h"
|
||||
#include "d3d11_shader.h"
|
||||
#include "d3d11_state.h"
|
||||
@ -31,7 +33,6 @@ namespace dxvk {
|
||||
class D3D11CommonShader;
|
||||
class D3D11CommonTexture;
|
||||
class D3D11Counter;
|
||||
class D3D11DeviceContext;
|
||||
class D3D11DXGIDevice;
|
||||
class D3D11ImmediateContext;
|
||||
class D3D11Predicate;
|
||||
@ -260,7 +261,7 @@ namespace dxvk {
|
||||
HRESULT STDMETHODCALLTYPE CreateFence(
|
||||
UINT64 InitialValue,
|
||||
D3D11_FENCE_FLAG Flags,
|
||||
REFIID ReturnedInterface,
|
||||
REFIID riid,
|
||||
void** ppFence);
|
||||
|
||||
void STDMETHODCALLTYPE ReadFromSubresource(
|
||||
@ -420,19 +421,23 @@ namespace dxvk {
|
||||
D3D10Device* GetD3D10Interface() const {
|
||||
return m_d3d10Device;
|
||||
}
|
||||
|
||||
static bool CheckFeatureLevelSupport(
|
||||
const Rc<DxvkInstance>& instance,
|
||||
const Rc<DxvkAdapter>& adapter,
|
||||
D3D_FEATURE_LEVEL featureLevel);
|
||||
|
||||
D3D11ImmediateContext* GetContext() const {
|
||||
return m_context.ptr();
|
||||
}
|
||||
|
||||
bool Is11on12Device() const;
|
||||
|
||||
static D3D_FEATURE_LEVEL GetMaxFeatureLevel(
|
||||
const Rc<DxvkInstance>& Instance,
|
||||
const Rc<DxvkAdapter>& Adapter);
|
||||
|
||||
static DxvkDeviceFeatures GetDeviceFeatures(
|
||||
const Rc<DxvkAdapter>& adapter,
|
||||
D3D_FEATURE_LEVEL featureLevel);
|
||||
const Rc<DxvkAdapter>& Adapter);
|
||||
|
||||
private:
|
||||
|
||||
IDXGIObject* m_container;
|
||||
D3D11DXGIDevice* m_container;
|
||||
|
||||
D3D_FEATURE_LEVEL m_featureLevel;
|
||||
UINT m_featureFlags;
|
||||
@ -455,7 +460,10 @@ namespace dxvk {
|
||||
D3D11StateObjectSet<D3D11RasterizerState> m_rsStateObjects;
|
||||
D3D11StateObjectSet<D3D11SamplerState> m_samplerObjects;
|
||||
D3D11ShaderModuleSet m_shaderModules;
|
||||
|
||||
|
||||
D3D_FEATURE_LEVEL m_maxFeatureLevel;
|
||||
D3D11DeviceFeatures m_deviceFeatures;
|
||||
|
||||
HRESULT CreateShaderModule(
|
||||
D3D11CommonShader* pShaderModule,
|
||||
DxvkShaderKey ShaderKey,
|
||||
@ -465,13 +473,14 @@ namespace dxvk {
|
||||
const DxbcModuleInfo* pModuleInfo);
|
||||
|
||||
HRESULT GetFormatSupportFlags(
|
||||
DXGI_FORMAT Format,
|
||||
UINT* pFlags1,
|
||||
UINT* pFlags2) const;
|
||||
DXGI_FORMAT Format,
|
||||
UINT* pFlags1,
|
||||
UINT* pFlags2) const;
|
||||
|
||||
BOOL GetImageTypeSupport(
|
||||
VkFormat Format,
|
||||
VkImageType Type) const;
|
||||
VkFormat Format,
|
||||
VkImageType Type,
|
||||
VkImageCreateFlags Flags) const;
|
||||
|
||||
template<bool IsKmtHandle>
|
||||
HRESULT OpenSharedResourceGeneric(
|
||||
@ -488,13 +497,10 @@ namespace dxvk {
|
||||
Void* pData,
|
||||
UINT RowPitch,
|
||||
UINT DepthPitch,
|
||||
ID3D11Resource* pResource,
|
||||
D3D11CommonTexture* pTexture,
|
||||
UINT Subresource,
|
||||
const D3D11_BOX* pBox);
|
||||
|
||||
static D3D_FEATURE_LEVEL GetMaxFeatureLevel(
|
||||
const Rc<DxvkInstance>& pInstance);
|
||||
|
||||
};
|
||||
|
||||
|
||||
@ -692,39 +698,36 @@ namespace dxvk {
|
||||
|
||||
|
||||
/**
|
||||
* \brief DXGI swap chain factory
|
||||
* \brief DXVK swap chain factory
|
||||
*/
|
||||
class WineDXGISwapChainFactory : public IWineDXGISwapChainFactory {
|
||||
|
||||
class DXGIVkSwapChainFactory : public IDXGIVkSwapChainFactory {
|
||||
|
||||
public:
|
||||
|
||||
WineDXGISwapChainFactory(
|
||||
|
||||
DXGIVkSwapChainFactory(
|
||||
D3D11DXGIDevice* pContainer,
|
||||
D3D11Device* pDevice);
|
||||
|
||||
|
||||
ULONG STDMETHODCALLTYPE AddRef();
|
||||
|
||||
|
||||
ULONG STDMETHODCALLTYPE Release();
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE QueryInterface(
|
||||
REFIID riid,
|
||||
void** ppvObject);
|
||||
|
||||
HRESULT STDMETHODCALLTYPE CreateSwapChainForHwnd(
|
||||
IDXGIFactory* pFactory,
|
||||
HWND hWnd,
|
||||
const DXGI_SWAP_CHAIN_DESC1* pDesc,
|
||||
const DXGI_SWAP_CHAIN_FULLSCREEN_DESC* pFullscreenDesc,
|
||||
IDXGIOutput* pRestrictToOutput,
|
||||
IDXGISwapChain1** ppSwapChain);
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE CreateSwapChain(
|
||||
IDXGIVkSurfaceFactory* pSurfaceFactory,
|
||||
const DXGI_SWAP_CHAIN_DESC1* pDesc,
|
||||
IDXGIVkSwapChain** ppSwapChain);
|
||||
|
||||
private:
|
||||
|
||||
|
||||
D3D11DXGIDevice* m_container;
|
||||
D3D11Device* m_device;
|
||||
|
||||
|
||||
};
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* \brief D3D11 device metadata shenanigans
|
||||
@ -768,8 +771,11 @@ namespace dxvk {
|
||||
|
||||
D3D11DXGIDevice(
|
||||
IDXGIAdapter* pAdapter,
|
||||
const Rc<DxvkInstance>& pDxvkInstance,
|
||||
const Rc<DxvkAdapter>& pDxvkAdapter,
|
||||
ID3D12Device* pD3D12Device,
|
||||
ID3D12CommandQueue* pD3D12Queue,
|
||||
Rc<DxvkInstance> pDxvkInstance,
|
||||
Rc<DxvkAdapter> pDxvkAdapter,
|
||||
Rc<DxvkDevice> pDxvkDevice,
|
||||
D3D_FEATURE_LEVEL FeatureLevel,
|
||||
UINT FeatureFlags);
|
||||
|
||||
@ -838,6 +844,10 @@ namespace dxvk {
|
||||
|
||||
Rc<DxvkDevice> STDMETHODCALLTYPE GetDXVKDevice();
|
||||
|
||||
BOOL Is11on12Device() const {
|
||||
return m_d3d11on12.Is11on12Device();
|
||||
}
|
||||
|
||||
private:
|
||||
|
||||
Com<IDXGIAdapter> m_dxgiAdapter;
|
||||
@ -850,14 +860,13 @@ namespace dxvk {
|
||||
D3D11DeviceExt m_d3d11DeviceExt;
|
||||
D3D11VkInterop m_d3d11Interop;
|
||||
D3D11VideoDevice m_d3d11Video;
|
||||
D3D11on12Device m_d3d11on12;
|
||||
DXGIDXVKDevice m_metaDevice;
|
||||
|
||||
WineDXGISwapChainFactory m_wineFactory;
|
||||
DXGIVkSwapChainFactory m_dxvkFactory;
|
||||
|
||||
uint32_t m_frameLatency = DefaultFrameLatency;
|
||||
|
||||
Rc<DxvkDevice> CreateDevice(D3D_FEATURE_LEVEL FeatureLevel);
|
||||
|
||||
};
|
||||
|
||||
}
|
||||
|
399
src/d3d11/d3d11_features.cpp
Normal file
399
src/d3d11/d3d11_features.cpp
Normal file
@ -0,0 +1,399 @@
|
||||
#include <array>
|
||||
|
||||
#include "d3d11_features.h"
|
||||
|
||||
namespace dxvk {
|
||||
|
||||
D3D11DeviceFeatures::D3D11DeviceFeatures() {
|
||||
|
||||
}
|
||||
|
||||
|
||||
D3D11DeviceFeatures::D3D11DeviceFeatures(
|
||||
const Rc<DxvkInstance>& Instance,
|
||||
const Rc<DxvkAdapter>& Adapter,
|
||||
D3D_FEATURE_LEVEL FeatureLevel)
|
||||
: m_features (Adapter->features()),
|
||||
m_properties (Adapter->devicePropertiesExt()) {
|
||||
// Assume no TBDR. DXVK does not optimize for TBDR architectures
|
||||
// anyway, and D3D11 does not really provide meaningful support.
|
||||
m_architectureInfo.TileBasedDeferredRenderer = FALSE;
|
||||
|
||||
// D3D9 options. We unconditionally support all of these.
|
||||
m_d3d9Options.FullNonPow2TextureSupport = TRUE;
|
||||
|
||||
m_d3d9Options1.FullNonPow2TextureSupported = TRUE;
|
||||
m_d3d9Options1.DepthAsTextureWithLessEqualComparisonFilterSupported = TRUE;
|
||||
m_d3d9Options1.SimpleInstancingSupported = TRUE;
|
||||
m_d3d9Options1.TextureCubeFaceRenderTargetWithNonCubeDepthStencilSupported = TRUE;
|
||||
|
||||
m_d3d9Shadow.SupportsDepthAsTextureWithLessEqualComparisonFilter = TRUE;
|
||||
|
||||
m_d3d9SimpleInstancing.SimpleInstancingSupported = TRUE;
|
||||
|
||||
// D3D10 options. We unconditionally support compute shaders.
|
||||
m_d3d10Options.ComputeShaders_Plus_RawAndStructuredBuffers_Via_Shader_4_x = TRUE;
|
||||
|
||||
// D3D11.1 options. All of these are required for Feature Level 11_1.
|
||||
auto sharedResourceTier = DetermineSharedResourceTier(Adapter, FeatureLevel);
|
||||
|
||||
bool hasDoublePrecisionSupport = m_features.core.features.shaderFloat64
|
||||
&& m_features.core.features.shaderInt64;
|
||||
|
||||
m_d3d11Options.DiscardAPIsSeenByDriver = TRUE;
|
||||
m_d3d11Options.FlagsForUpdateAndCopySeenByDriver = TRUE;
|
||||
m_d3d11Options.ClearView = TRUE;
|
||||
m_d3d11Options.CopyWithOverlap = TRUE;
|
||||
m_d3d11Options.ConstantBufferPartialUpdate = TRUE;
|
||||
m_d3d11Options.ConstantBufferOffsetting = TRUE;
|
||||
m_d3d11Options.MapNoOverwriteOnDynamicConstantBuffer = TRUE;
|
||||
m_d3d11Options.MapNoOverwriteOnDynamicBufferSRV = TRUE;
|
||||
m_d3d11Options.ExtendedResourceSharing = sharedResourceTier > D3D11_SHARED_RESOURCE_TIER_0;
|
||||
|
||||
if (FeatureLevel >= D3D_FEATURE_LEVEL_10_0) {
|
||||
m_d3d11Options.OutputMergerLogicOp = m_features.core.features.logicOp;
|
||||
m_d3d11Options.MultisampleRTVWithForcedSampleCountOne = TRUE; // Not really
|
||||
}
|
||||
|
||||
if (FeatureLevel >= D3D_FEATURE_LEVEL_11_0) {
|
||||
m_d3d11Options.UAVOnlyRenderingForcedSampleCount = TRUE;
|
||||
m_d3d11Options.SAD4ShaderInstructions = TRUE;
|
||||
m_d3d11Options.ExtendedDoublesShaderInstructions = hasDoublePrecisionSupport;
|
||||
}
|
||||
|
||||
// D3D11.2 options.
|
||||
auto tiledResourcesTier = DetermineTiledResourcesTier(FeatureLevel);
|
||||
m_d3d11Options1.TiledResourcesTier = tiledResourcesTier;
|
||||
m_d3d11Options1.MinMaxFiltering = tiledResourcesTier >= D3D11_TILED_RESOURCES_TIER_2;
|
||||
m_d3d11Options1.ClearViewAlsoSupportsDepthOnlyFormats = TRUE;
|
||||
|
||||
if (FeatureLevel >= D3D_FEATURE_LEVEL_11_0)
|
||||
m_d3d11Options1.MapOnDefaultBuffers = TRUE;
|
||||
|
||||
// D3D11.3 options
|
||||
m_d3d11Options2.TypedUAVLoadAdditionalFormats = DetermineUavExtendedTypedLoadSupport(Adapter, FeatureLevel);
|
||||
m_d3d11Options2.ConservativeRasterizationTier = DetermineConservativeRasterizationTier(FeatureLevel);
|
||||
m_d3d11Options2.TiledResourcesTier = tiledResourcesTier;
|
||||
m_d3d11Options2.StandardSwizzle = FALSE;
|
||||
m_d3d11Options2.UnifiedMemoryArchitecture = FALSE;
|
||||
|
||||
if (FeatureLevel >= D3D_FEATURE_LEVEL_11_0)
|
||||
m_d3d11Options2.MapOnDefaultTextures = TRUE;
|
||||
|
||||
if (FeatureLevel >= D3D_FEATURE_LEVEL_11_1) {
|
||||
m_d3d11Options2.ROVsSupported = m_features.extFragmentShaderInterlock.fragmentShaderPixelInterlock;
|
||||
m_d3d11Options2.PSSpecifiedStencilRefSupported = m_features.extShaderStencilExport;
|
||||
}
|
||||
|
||||
// More D3D11.3 options
|
||||
if (FeatureLevel >= D3D_FEATURE_LEVEL_11_0) {
|
||||
m_d3d11Options3.VPAndRTArrayIndexFromAnyShaderFeedingRasterizer =
|
||||
m_features.vk12.shaderOutputViewportIndex &&
|
||||
m_features.vk12.shaderOutputLayer;
|
||||
}
|
||||
|
||||
// D3D11.4 options
|
||||
m_d3d11Options4.ExtendedNV12SharedTextureSupported = sharedResourceTier > D3D11_SHARED_RESOURCE_TIER_0;
|
||||
|
||||
// More D3D11.4 options
|
||||
m_d3d11Options5.SharedResourceTier = sharedResourceTier;
|
||||
|
||||
// Double-precision support
|
||||
if (FeatureLevel >= D3D_FEATURE_LEVEL_11_0)
|
||||
m_doubles.DoublePrecisionFloatShaderOps = hasDoublePrecisionSupport;
|
||||
|
||||
// These numbers are not accurate, but we have no real way to query these
|
||||
m_gpuVirtualAddress.MaxGPUVirtualAddressBitsPerResource = 32;
|
||||
m_gpuVirtualAddress.MaxGPUVirtualAddressBitsPerProcess = 40;
|
||||
|
||||
// Marker support only depends on the debug utils extension
|
||||
m_marker.Profile = Instance->extensions().extDebugUtils;
|
||||
|
||||
// DXVK will keep all shaders in memory once created, and all Vulkan
|
||||
// drivers that we know of that can run DXVK have an on-disk cache.
|
||||
m_shaderCache.SupportFlags = D3D11_SHADER_CACHE_SUPPORT_AUTOMATIC_INPROC_CACHE
|
||||
| D3D11_SHADER_CACHE_SUPPORT_AUTOMATIC_DISK_CACHE;
|
||||
|
||||
// DXVK does not support min precision
|
||||
m_shaderMinPrecision.PixelShaderMinPrecision = 0;
|
||||
m_shaderMinPrecision.AllOtherShaderStagesMinPrecision = 0;
|
||||
|
||||
// Report native support for command lists here so that we do not actually have
|
||||
// to re-implement the UpdateSubresource bug from the D3D11 runtime, see MSDN:
|
||||
// https://msdn.microsoft.com/en-us/library/windows/desktop/ff476486(v=vs.85).aspx)
|
||||
m_threading.DriverConcurrentCreates = TRUE;
|
||||
m_threading.DriverCommandLists = TRUE;
|
||||
}
|
||||
|
||||
|
||||
D3D11DeviceFeatures::~D3D11DeviceFeatures() {
|
||||
|
||||
}
|
||||
|
||||
|
||||
HRESULT D3D11DeviceFeatures::GetFeatureData(
|
||||
D3D11_FEATURE Feature,
|
||||
UINT FeatureDataSize,
|
||||
void* pFeatureData) const {
|
||||
switch (Feature) {
|
||||
case D3D11_FEATURE_ARCHITECTURE_INFO:
|
||||
return GetTypedFeatureData(FeatureDataSize, pFeatureData, &m_architectureInfo);
|
||||
case D3D11_FEATURE_D3D9_OPTIONS:
|
||||
return GetTypedFeatureData(FeatureDataSize, pFeatureData, &m_d3d9Options);
|
||||
case D3D11_FEATURE_D3D9_OPTIONS1:
|
||||
return GetTypedFeatureData(FeatureDataSize, pFeatureData, &m_d3d9Options1);
|
||||
case D3D11_FEATURE_D3D9_SHADOW_SUPPORT:
|
||||
return GetTypedFeatureData(FeatureDataSize, pFeatureData, &m_d3d9Shadow);
|
||||
case D3D11_FEATURE_D3D9_SIMPLE_INSTANCING_SUPPORT:
|
||||
return GetTypedFeatureData(FeatureDataSize, pFeatureData, &m_d3d9SimpleInstancing);
|
||||
case D3D11_FEATURE_D3D10_X_HARDWARE_OPTIONS:
|
||||
return GetTypedFeatureData(FeatureDataSize, pFeatureData, &m_d3d10Options);
|
||||
case D3D11_FEATURE_D3D11_OPTIONS:
|
||||
return GetTypedFeatureData(FeatureDataSize, pFeatureData, &m_d3d11Options);
|
||||
case D3D11_FEATURE_D3D11_OPTIONS1:
|
||||
return GetTypedFeatureData(FeatureDataSize, pFeatureData, &m_d3d11Options1);
|
||||
case D3D11_FEATURE_D3D11_OPTIONS2:
|
||||
return GetTypedFeatureData(FeatureDataSize, pFeatureData, &m_d3d11Options2);
|
||||
case D3D11_FEATURE_D3D11_OPTIONS3:
|
||||
return GetTypedFeatureData(FeatureDataSize, pFeatureData, &m_d3d11Options3);
|
||||
case D3D11_FEATURE_D3D11_OPTIONS4:
|
||||
return GetTypedFeatureData(FeatureDataSize, pFeatureData, &m_d3d11Options4);
|
||||
case D3D11_FEATURE_D3D11_OPTIONS5:
|
||||
return GetTypedFeatureData(FeatureDataSize, pFeatureData, &m_d3d11Options5);
|
||||
case D3D11_FEATURE_DOUBLES:
|
||||
return GetTypedFeatureData(FeatureDataSize, pFeatureData, &m_doubles);
|
||||
case D3D11_FEATURE_GPU_VIRTUAL_ADDRESS_SUPPORT:
|
||||
return GetTypedFeatureData(FeatureDataSize, pFeatureData, &m_gpuVirtualAddress);
|
||||
case D3D11_FEATURE_MARKER_SUPPORT:
|
||||
return GetTypedFeatureData(FeatureDataSize, pFeatureData, &m_marker);
|
||||
case D3D11_FEATURE_SHADER_CACHE:
|
||||
return GetTypedFeatureData(FeatureDataSize, pFeatureData, &m_shaderCache);
|
||||
case D3D11_FEATURE_SHADER_MIN_PRECISION_SUPPORT:
|
||||
return GetTypedFeatureData(FeatureDataSize, pFeatureData, &m_shaderMinPrecision);
|
||||
case D3D11_FEATURE_THREADING:
|
||||
return GetTypedFeatureData(FeatureDataSize, pFeatureData, &m_threading);
|
||||
default:
|
||||
Logger::err(str::format("D3D11: Unknown feature: ", Feature));
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
D3D_FEATURE_LEVEL D3D11DeviceFeatures::GetMaxFeatureLevel(
|
||||
const Rc<DxvkInstance>& Instance,
|
||||
const Rc<DxvkAdapter>& Adapter) {
|
||||
D3D11DeviceFeatures features(Instance, Adapter, D3D_FEATURE_LEVEL_12_1);
|
||||
return features.GetMaxFeatureLevel();
|
||||
}
|
||||
|
||||
|
||||
D3D11_CONSERVATIVE_RASTERIZATION_TIER D3D11DeviceFeatures::DetermineConservativeRasterizationTier(
|
||||
D3D_FEATURE_LEVEL FeatureLevel) {
|
||||
if (FeatureLevel < D3D_FEATURE_LEVEL_11_1
|
||||
|| !m_features.extConservativeRasterization)
|
||||
return D3D11_CONSERVATIVE_RASTERIZATION_NOT_SUPPORTED;
|
||||
|
||||
// We don't really have a way to query uncertainty regions,
|
||||
// so just check degenerate triangle behaviour
|
||||
if (!m_properties.extConservativeRasterization.degenerateTrianglesRasterized)
|
||||
return D3D11_CONSERVATIVE_RASTERIZATION_TIER_1;
|
||||
|
||||
// Inner coverage is required for Tier 3 support
|
||||
if (!m_properties.extConservativeRasterization.fullyCoveredFragmentShaderInputVariable)
|
||||
return D3D11_CONSERVATIVE_RASTERIZATION_TIER_2;
|
||||
|
||||
return D3D11_CONSERVATIVE_RASTERIZATION_TIER_3;
|
||||
}
|
||||
|
||||
|
||||
D3D11_SHARED_RESOURCE_TIER D3D11DeviceFeatures::DetermineSharedResourceTier(
|
||||
const Rc<DxvkAdapter>& Adapter,
|
||||
D3D_FEATURE_LEVEL FeatureLevel) {
|
||||
static std::atomic<bool> s_errorShown = { false };
|
||||
|
||||
// Lie about supporting Tier 1 since that's the
|
||||
// minimum required tier for Feature Level 11_1
|
||||
if (!Adapter->features().khrExternalMemoryWin32) {
|
||||
if (!s_errorShown.exchange(true))
|
||||
Logger::warn("D3D11DeviceFeatures: External memory features not supported");
|
||||
|
||||
return D3D11_SHARED_RESOURCE_TIER_1;
|
||||
}
|
||||
|
||||
// Check support for extended formats. Ignore multi-plane
|
||||
// formats here since driver support varies too much.
|
||||
std::array<VkFormat, 30> requiredFormats = {{
|
||||
VK_FORMAT_R16G16B16A16_SFLOAT,
|
||||
VK_FORMAT_R32G32B32A32_SFLOAT,
|
||||
VK_FORMAT_R32G32B32A32_UINT,
|
||||
VK_FORMAT_R32G32B32A32_SINT,
|
||||
VK_FORMAT_R16G16B16A16_SFLOAT,
|
||||
VK_FORMAT_R16G16B16A16_UNORM,
|
||||
VK_FORMAT_R16G16B16A16_UINT,
|
||||
VK_FORMAT_R16G16B16A16_SNORM,
|
||||
VK_FORMAT_R16G16B16A16_SINT,
|
||||
VK_FORMAT_A2B10G10R10_UNORM_PACK32,
|
||||
VK_FORMAT_A2B10G10R10_UINT_PACK32,
|
||||
VK_FORMAT_R8G8B8A8_UNORM,
|
||||
VK_FORMAT_R8G8B8A8_SRGB,
|
||||
VK_FORMAT_R8G8B8A8_UINT,
|
||||
VK_FORMAT_R8G8B8A8_SNORM,
|
||||
VK_FORMAT_R8G8B8A8_SINT,
|
||||
VK_FORMAT_B8G8R8A8_UNORM,
|
||||
VK_FORMAT_B8G8R8A8_SRGB,
|
||||
VK_FORMAT_R32_SFLOAT,
|
||||
VK_FORMAT_R32_UINT,
|
||||
VK_FORMAT_R32_SINT,
|
||||
VK_FORMAT_R16_SFLOAT,
|
||||
VK_FORMAT_R16_UNORM,
|
||||
VK_FORMAT_R16_UINT,
|
||||
VK_FORMAT_R16_SNORM,
|
||||
VK_FORMAT_R16_SINT,
|
||||
VK_FORMAT_R8_UNORM,
|
||||
VK_FORMAT_R8_UINT,
|
||||
VK_FORMAT_R8_SNORM,
|
||||
VK_FORMAT_R8_SINT,
|
||||
}};
|
||||
|
||||
bool allKmtHandlesSupported = true;
|
||||
bool allNtHandlesSupported = true;
|
||||
|
||||
for (auto f : requiredFormats) {
|
||||
allKmtHandlesSupported &= CheckFormatSharingSupport(Adapter, f, VK_EXTERNAL_MEMORY_HANDLE_TYPE_OPAQUE_WIN32_KMT_BIT);
|
||||
allNtHandlesSupported &= CheckFormatSharingSupport(Adapter, f, VK_EXTERNAL_MEMORY_HANDLE_TYPE_OPAQUE_WIN32_BIT);
|
||||
}
|
||||
|
||||
// Again, lie about at least tier 1 support
|
||||
if (!allKmtHandlesSupported) {
|
||||
if (!s_errorShown.exchange(true))
|
||||
Logger::warn("D3D11DeviceFeatures: Some formats not supported for resource sharing");
|
||||
return D3D11_SHARED_RESOURCE_TIER_1;
|
||||
}
|
||||
|
||||
// Tier 2 requires all the above formats to be shareable
|
||||
// with NT handles in order to support D3D12 interop
|
||||
if (!allNtHandlesSupported)
|
||||
return D3D11_SHARED_RESOURCE_TIER_1;
|
||||
|
||||
// Tier 3 additionally requires R11G11B10 to be
|
||||
// shareable with D3D12
|
||||
if (!CheckFormatSharingSupport(Adapter, VK_FORMAT_B10G11R11_UFLOAT_PACK32, VK_EXTERNAL_MEMORY_HANDLE_TYPE_OPAQUE_WIN32_BIT))
|
||||
return D3D11_SHARED_RESOURCE_TIER_2;
|
||||
|
||||
return D3D11_SHARED_RESOURCE_TIER_3;
|
||||
}
|
||||
|
||||
|
||||
D3D11_TILED_RESOURCES_TIER D3D11DeviceFeatures::DetermineTiledResourcesTier(
|
||||
D3D_FEATURE_LEVEL FeatureLevel) {
|
||||
if (FeatureLevel < D3D_FEATURE_LEVEL_11_0
|
||||
|| !m_features.core.features.sparseBinding
|
||||
|| !m_features.core.features.sparseResidencyBuffer
|
||||
|| !m_features.core.features.sparseResidencyImage2D
|
||||
|| !m_features.core.features.sparseResidencyAliased
|
||||
|| !m_properties.core.properties.sparseProperties.residencyStandard2DBlockShape)
|
||||
return D3D11_TILED_RESOURCES_NOT_SUPPORTED;
|
||||
|
||||
if (FeatureLevel < D3D_FEATURE_LEVEL_11_1
|
||||
|| !m_features.core.features.shaderResourceResidency
|
||||
|| !m_features.core.features.shaderResourceMinLod
|
||||
|| !m_features.vk12.samplerFilterMinmax
|
||||
|| !m_properties.vk12.filterMinmaxSingleComponentFormats
|
||||
|| !m_properties.core.properties.sparseProperties.residencyNonResidentStrict
|
||||
|| m_properties.core.properties.sparseProperties.residencyAlignedMipSize)
|
||||
return D3D11_TILED_RESOURCES_TIER_1;
|
||||
|
||||
if (!m_features.core.features.sparseResidencyImage3D
|
||||
|| !m_properties.core.properties.sparseProperties.residencyStandard3DBlockShape)
|
||||
return D3D11_TILED_RESOURCES_TIER_2;
|
||||
|
||||
return D3D11_TILED_RESOURCES_TIER_3;
|
||||
}
|
||||
|
||||
|
||||
BOOL D3D11DeviceFeatures::DetermineUavExtendedTypedLoadSupport(
|
||||
const Rc<DxvkAdapter>& Adapter,
|
||||
D3D_FEATURE_LEVEL FeatureLevel) {
|
||||
static const std::array<VkFormat, 18> s_formats = {{
|
||||
VK_FORMAT_R32_SFLOAT,
|
||||
VK_FORMAT_R32_UINT,
|
||||
VK_FORMAT_R32_SINT,
|
||||
VK_FORMAT_R32G32B32A32_SFLOAT,
|
||||
VK_FORMAT_R32G32B32A32_UINT,
|
||||
VK_FORMAT_R32G32B32A32_SINT,
|
||||
VK_FORMAT_R16G16B16A16_SFLOAT,
|
||||
VK_FORMAT_R16G16B16A16_UINT,
|
||||
VK_FORMAT_R16G16B16A16_SINT,
|
||||
VK_FORMAT_R8G8B8A8_UNORM,
|
||||
VK_FORMAT_R8G8B8A8_UINT,
|
||||
VK_FORMAT_R8G8B8A8_SINT,
|
||||
VK_FORMAT_R16_SFLOAT,
|
||||
VK_FORMAT_R16_UINT,
|
||||
VK_FORMAT_R16_SINT,
|
||||
VK_FORMAT_R8_UNORM,
|
||||
VK_FORMAT_R8_UINT,
|
||||
VK_FORMAT_R8_SINT,
|
||||
}};
|
||||
|
||||
if (FeatureLevel < D3D_FEATURE_LEVEL_11_0)
|
||||
return FALSE;
|
||||
|
||||
for (auto f : s_formats) {
|
||||
DxvkFormatFeatures features = Adapter->getFormatFeatures(f);
|
||||
VkFormatFeatureFlags2 imgFeatures = features.optimal | features.linear;
|
||||
|
||||
if (!(imgFeatures & VK_FORMAT_FEATURE_2_STORAGE_READ_WITHOUT_FORMAT_BIT))
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
|
||||
BOOL D3D11DeviceFeatures::CheckFormatSharingSupport(
|
||||
const Rc<DxvkAdapter>& Adapter,
|
||||
VkFormat Format,
|
||||
VkExternalMemoryHandleTypeFlagBits HandleType) {
|
||||
DxvkFormatQuery query = { };
|
||||
query.format = Format;
|
||||
query.type = VK_IMAGE_TYPE_2D;
|
||||
query.tiling = VK_IMAGE_TILING_OPTIMAL;
|
||||
query.usage = VK_IMAGE_USAGE_SAMPLED_BIT;
|
||||
query.handleType = HandleType;
|
||||
|
||||
constexpr VkExternalMemoryFeatureFlags featureMask
|
||||
= VK_EXTERNAL_MEMORY_FEATURE_EXPORTABLE_BIT
|
||||
| VK_EXTERNAL_MEMORY_FEATURE_IMPORTABLE_BIT;
|
||||
|
||||
auto limits = Adapter->getFormatLimits(query);
|
||||
return limits && (limits->externalFeatures & featureMask);
|
||||
}
|
||||
|
||||
|
||||
D3D_FEATURE_LEVEL D3D11DeviceFeatures::GetMaxFeatureLevel() const {
|
||||
// Check Feature Level 11_0 features
|
||||
if (!m_features.core.features.drawIndirectFirstInstance
|
||||
|| !m_features.core.features.fragmentStoresAndAtomics
|
||||
|| !m_features.core.features.multiDrawIndirect
|
||||
|| !m_features.core.features.tessellationShader)
|
||||
return D3D_FEATURE_LEVEL_10_1;
|
||||
|
||||
// Check Feature Level 11_1 features
|
||||
if (!m_d3d11Options.OutputMergerLogicOp
|
||||
|| !m_features.core.features.vertexPipelineStoresAndAtomics)
|
||||
return D3D_FEATURE_LEVEL_11_0;
|
||||
|
||||
// Check Feature Level 12_0 features
|
||||
if (m_d3d11Options2.TiledResourcesTier < D3D11_TILED_RESOURCES_TIER_2
|
||||
|| !m_d3d11Options2.TypedUAVLoadAdditionalFormats)
|
||||
return D3D_FEATURE_LEVEL_11_1;
|
||||
|
||||
// Check Feature Level 12_1 features
|
||||
if (!m_d3d11Options2.ConservativeRasterizationTier
|
||||
|| !m_d3d11Options2.ROVsSupported)
|
||||
return D3D_FEATURE_LEVEL_12_0;
|
||||
|
||||
return D3D_FEATURE_LEVEL_12_1;
|
||||
}
|
||||
|
||||
}
|
124
src/d3d11/d3d11_features.h
Normal file
124
src/d3d11/d3d11_features.h
Normal file
@ -0,0 +1,124 @@
|
||||
#pragma once
|
||||
|
||||
#include "d3d11_include.h"
|
||||
|
||||
#include "../dxvk/dxvk_adapter.h"
|
||||
#include "../dxvk/dxvk_instance.h"
|
||||
|
||||
namespace dxvk {
|
||||
|
||||
/**
|
||||
* \brief Device features
|
||||
*
|
||||
* Stores D3D device feature structs.
|
||||
*/
|
||||
class D3D11DeviceFeatures {
|
||||
|
||||
public:
|
||||
|
||||
D3D11DeviceFeatures();
|
||||
|
||||
D3D11DeviceFeatures(
|
||||
const Rc<DxvkInstance>& Instance,
|
||||
const Rc<DxvkAdapter>& Adapter,
|
||||
D3D_FEATURE_LEVEL FeatureLevel);
|
||||
|
||||
~D3D11DeviceFeatures();
|
||||
|
||||
/**
|
||||
* \brief Retrieves feature support data
|
||||
*
|
||||
* \param [in] Feature D3D feature to query
|
||||
* \param [in] FeatureDataSize Data size, in bytes
|
||||
* \param [out] pFeatureData Data
|
||||
* \returns Status of the operation
|
||||
*/
|
||||
HRESULT GetFeatureData(
|
||||
D3D11_FEATURE Feature,
|
||||
UINT FeatureDataSize,
|
||||
void* pFeatureData) const;
|
||||
|
||||
/**
|
||||
* \brief Queries tiled resources tier
|
||||
* \returns Tiled resources tier
|
||||
*/
|
||||
D3D11_TILED_RESOURCES_TIER GetTiledResourcesTier() const {
|
||||
return m_d3d11Options2.TiledResourcesTier;
|
||||
}
|
||||
|
||||
/**
|
||||
* \brief Queries conservative rasterization tier
|
||||
* \returns Conservative rasterization tier
|
||||
*/
|
||||
D3D11_CONSERVATIVE_RASTERIZATION_TIER GetConservativeRasterizationTier() const {
|
||||
return m_d3d11Options2.ConservativeRasterizationTier;
|
||||
}
|
||||
|
||||
/**
|
||||
* \brief Tests maximum supported feature level
|
||||
*
|
||||
* \param [in] Instance DXVK instance
|
||||
* \param [in] Adapter DXVK adapter
|
||||
* \returns Highest supported feature level
|
||||
*/
|
||||
static D3D_FEATURE_LEVEL GetMaxFeatureLevel(
|
||||
const Rc<DxvkInstance>& Instance,
|
||||
const Rc<DxvkAdapter>& Adapter);
|
||||
|
||||
private:
|
||||
|
||||
DxvkDeviceFeatures m_features;
|
||||
DxvkDeviceInfo m_properties;
|
||||
|
||||
D3D11_FEATURE_DATA_ARCHITECTURE_INFO m_architectureInfo = { };
|
||||
D3D11_FEATURE_DATA_D3D9_OPTIONS m_d3d9Options = { };
|
||||
D3D11_FEATURE_DATA_D3D9_OPTIONS1 m_d3d9Options1 = { };
|
||||
D3D11_FEATURE_DATA_D3D9_SHADOW_SUPPORT m_d3d9Shadow = { };
|
||||
D3D11_FEATURE_DATA_D3D9_SIMPLE_INSTANCING_SUPPORT m_d3d9SimpleInstancing = { };
|
||||
D3D11_FEATURE_DATA_D3D10_X_HARDWARE_OPTIONS m_d3d10Options = { };
|
||||
D3D11_FEATURE_DATA_D3D11_OPTIONS m_d3d11Options = { };
|
||||
D3D11_FEATURE_DATA_D3D11_OPTIONS1 m_d3d11Options1 = { };
|
||||
D3D11_FEATURE_DATA_D3D11_OPTIONS2 m_d3d11Options2 = { };
|
||||
D3D11_FEATURE_DATA_D3D11_OPTIONS3 m_d3d11Options3 = { };
|
||||
D3D11_FEATURE_DATA_D3D11_OPTIONS4 m_d3d11Options4 = { };
|
||||
D3D11_FEATURE_DATA_D3D11_OPTIONS5 m_d3d11Options5 = { };
|
||||
D3D11_FEATURE_DATA_DOUBLES m_doubles = { };
|
||||
D3D11_FEATURE_DATA_GPU_VIRTUAL_ADDRESS_SUPPORT m_gpuVirtualAddress = { };
|
||||
D3D11_FEATURE_DATA_MARKER_SUPPORT m_marker = { };
|
||||
D3D11_FEATURE_DATA_SHADER_CACHE m_shaderCache = { };
|
||||
D3D11_FEATURE_DATA_SHADER_MIN_PRECISION_SUPPORT m_shaderMinPrecision = { };
|
||||
D3D11_FEATURE_DATA_THREADING m_threading = { };
|
||||
|
||||
template<typename T>
|
||||
static HRESULT GetTypedFeatureData(UINT Size, void* pDstData, const T* pSrcData) {
|
||||
if (Size != sizeof(T))
|
||||
return E_INVALIDARG;
|
||||
|
||||
*(reinterpret_cast<T*>(pDstData)) = *pSrcData;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
D3D11_CONSERVATIVE_RASTERIZATION_TIER DetermineConservativeRasterizationTier(
|
||||
D3D_FEATURE_LEVEL FeatureLevel);
|
||||
|
||||
D3D11_SHARED_RESOURCE_TIER DetermineSharedResourceTier(
|
||||
const Rc<DxvkAdapter>& Adapter,
|
||||
D3D_FEATURE_LEVEL FeatureLevel);
|
||||
|
||||
D3D11_TILED_RESOURCES_TIER DetermineTiledResourcesTier(
|
||||
D3D_FEATURE_LEVEL FeatureLevel);
|
||||
|
||||
BOOL DetermineUavExtendedTypedLoadSupport(
|
||||
const Rc<DxvkAdapter>& Adapter,
|
||||
D3D_FEATURE_LEVEL FeatureLevel);
|
||||
|
||||
BOOL CheckFormatSharingSupport(
|
||||
const Rc<DxvkAdapter>& Adapter,
|
||||
VkFormat Format,
|
||||
VkExternalMemoryHandleTypeFlagBits HandleType);
|
||||
|
||||
D3D_FEATURE_LEVEL GetMaxFeatureLevel() const;
|
||||
|
||||
};
|
||||
|
||||
}
|
105
src/d3d11/d3d11_fence.cpp
Normal file
105
src/d3d11/d3d11_fence.cpp
Normal file
@ -0,0 +1,105 @@
|
||||
#include "d3d11_fence.h"
|
||||
#include "d3d11_device.h"
|
||||
#include "../util/util_win32_compat.h"
|
||||
|
||||
namespace dxvk {
|
||||
|
||||
D3D11Fence::D3D11Fence(
|
||||
D3D11Device* pDevice,
|
||||
UINT64 InitialValue,
|
||||
D3D11_FENCE_FLAG Flags,
|
||||
HANDLE hFence)
|
||||
: D3D11DeviceChild<ID3D11Fence>(pDevice) {
|
||||
DxvkFenceCreateInfo fenceInfo;
|
||||
fenceInfo.initialValue = InitialValue;
|
||||
m_flags = Flags;
|
||||
|
||||
if (Flags & D3D11_FENCE_FLAG_SHARED) {
|
||||
fenceInfo.sharedType = VK_EXTERNAL_SEMAPHORE_HANDLE_TYPE_D3D11_FENCE_BIT;
|
||||
if (hFence == nullptr)
|
||||
hFence = INVALID_HANDLE_VALUE;
|
||||
fenceInfo.sharedHandle = hFence;
|
||||
}
|
||||
|
||||
if (Flags & ~D3D11_FENCE_FLAG_SHARED)
|
||||
Logger::err(str::format("Fence flags 0x", std::hex, Flags, " not supported"));
|
||||
|
||||
m_fence = pDevice->GetDXVKDevice()->createFence(fenceInfo);
|
||||
}
|
||||
|
||||
|
||||
D3D11Fence::~D3D11Fence() {
|
||||
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D11Fence::QueryInterface(
|
||||
REFIID riid,
|
||||
void** ppvObject) {
|
||||
if (ppvObject == nullptr)
|
||||
return E_POINTER;
|
||||
|
||||
*ppvObject = nullptr;
|
||||
|
||||
if (riid == __uuidof(IUnknown)
|
||||
|| riid == __uuidof(ID3D11DeviceChild)
|
||||
|| riid == __uuidof(ID3D11Fence)) {
|
||||
*ppvObject = ref(this);
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
if (logQueryInterfaceError(__uuidof(ID3D11Fence), riid)) {
|
||||
Logger::warn("D3D11Fence: Unknown interface query");
|
||||
Logger::warn(str::format(riid));
|
||||
}
|
||||
|
||||
return E_NOINTERFACE;
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D11Fence::CreateSharedHandle(
|
||||
const SECURITY_ATTRIBUTES* pAttributes,
|
||||
DWORD dwAccess,
|
||||
LPCWSTR lpName,
|
||||
HANDLE* pHandle) {
|
||||
if (!(m_flags & D3D11_FENCE_FLAG_SHARED))
|
||||
return E_INVALIDARG;
|
||||
|
||||
if (pAttributes)
|
||||
Logger::warn(str::format("CreateSharedHandle: attributes ", pAttributes, " not handled"));
|
||||
if (dwAccess)
|
||||
Logger::warn(str::format("CreateSharedHandle: access ", dwAccess, " not handled"));
|
||||
if (lpName)
|
||||
Logger::warn(str::format("CreateSharedHandle: name ", dxvk::str::fromws(lpName), " not handled"));
|
||||
|
||||
HANDLE sharedHandle = m_fence->sharedHandle();
|
||||
if (sharedHandle == INVALID_HANDLE_VALUE)
|
||||
return E_INVALIDARG;
|
||||
|
||||
*pHandle = sharedHandle;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D11Fence::SetEventOnCompletion(
|
||||
UINT64 Value,
|
||||
HANDLE hEvent) {
|
||||
if (hEvent) {
|
||||
m_fence->enqueueWait(Value, [hEvent] {
|
||||
SetEvent(hEvent);
|
||||
});
|
||||
} else {
|
||||
m_fence->wait(Value);
|
||||
}
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
UINT64 STDMETHODCALLTYPE D3D11Fence::GetCompletedValue() {
|
||||
// TODO in the case of rewinds, the stored value may be higher.
|
||||
// For shared fences, calling vkGetSemaphoreCounterValue here could alleviate the issue.
|
||||
|
||||
return m_fence->getValue();
|
||||
}
|
||||
|
||||
}
|
49
src/d3d11/d3d11_fence.h
Normal file
49
src/d3d11/d3d11_fence.h
Normal file
@ -0,0 +1,49 @@
|
||||
#pragma once
|
||||
|
||||
#include "../dxvk/dxvk_fence.h"
|
||||
#include "../dxvk/dxvk_gpu_query.h"
|
||||
|
||||
#include "d3d11_device_child.h"
|
||||
|
||||
namespace dxvk {
|
||||
|
||||
class D3D11Fence : public D3D11DeviceChild<ID3D11Fence> {
|
||||
|
||||
public:
|
||||
|
||||
D3D11Fence(
|
||||
D3D11Device* pDevice,
|
||||
UINT64 InitialValue,
|
||||
D3D11_FENCE_FLAG Flags,
|
||||
HANDLE hFence);
|
||||
|
||||
~D3D11Fence();
|
||||
|
||||
HRESULT STDMETHODCALLTYPE QueryInterface(
|
||||
REFIID riid,
|
||||
void** ppvObject);
|
||||
|
||||
HRESULT STDMETHODCALLTYPE CreateSharedHandle(
|
||||
const SECURITY_ATTRIBUTES* pAttributes,
|
||||
DWORD dwAccess,
|
||||
LPCWSTR lpName,
|
||||
HANDLE* pHandle);
|
||||
|
||||
HRESULT STDMETHODCALLTYPE SetEventOnCompletion(
|
||||
UINT64 Value,
|
||||
HANDLE hEvent);
|
||||
|
||||
UINT64 STDMETHODCALLTYPE GetCompletedValue();
|
||||
|
||||
Rc<DxvkFence> GetFence() const {
|
||||
return m_fence;
|
||||
}
|
||||
|
||||
private:
|
||||
|
||||
Rc<DxvkFence> m_fence;
|
||||
D3D11_FENCE_FLAG m_flags;
|
||||
|
||||
};
|
||||
|
||||
}
|
@ -3,6 +3,7 @@
|
||||
#include "d3d11_gdi.h"
|
||||
|
||||
#include "../util/util_gdi.h"
|
||||
#include "../util/util_win32_compat.h"
|
||||
|
||||
namespace dxvk {
|
||||
|
||||
@ -149,11 +150,8 @@ namespace dxvk {
|
||||
HRESULT D3D11GDISurface::CreateReadbackResource() {
|
||||
auto tex = GetCommonTexture(m_resource);
|
||||
|
||||
Com<ID3D11Device> device;
|
||||
Com<ID3D11DeviceContext> context;
|
||||
|
||||
Com<ID3D11Device> device;
|
||||
m_resource->GetDevice(&device);
|
||||
device->GetImmediateContext(&context);
|
||||
|
||||
D3D11_RESOURCE_DIMENSION dim = { };
|
||||
m_resource->GetType(&dim);
|
||||
|
@ -3,44 +3,3 @@
|
||||
#include "../dxgi/dxgi_include.h"
|
||||
|
||||
#include <d3d11_4.h>
|
||||
|
||||
// This is not defined in the mingw headers
|
||||
#ifndef D3D11_1_UAV_SLOT_COUNT
|
||||
#define D3D11_1_UAV_SLOT_COUNT 64
|
||||
#endif
|
||||
|
||||
#ifndef D3D11_KEEP_RENDER_TARGETS_AND_DEPTH_STENCIL
|
||||
#define D3D11_KEEP_RENDER_TARGETS_AND_DEPTH_STENCIL 0xFFFFFFFF
|
||||
#endif
|
||||
|
||||
#ifndef D3D11_KEEP_UNORDERED_ACCESS_VIEWS
|
||||
#define D3D11_KEEP_UNORDERED_ACCESS_VIEWS 0xFFFFFFFF
|
||||
#endif
|
||||
|
||||
#define D3D11_DXVK_USE_REMAINING_LAYERS 0xFFFFFFFF
|
||||
#define D3D11_DXVK_USE_REMAINING_LEVELS 0xFFFFFFFF
|
||||
|
||||
// Most of these were copied from d3d11.h
|
||||
// For some strange reason, we cannot use the structures
|
||||
// directly, although others from the same header work.
|
||||
// Some structures are missing from the mingw headers.
|
||||
#ifndef _MSC_VER
|
||||
#if !defined(__MINGW64_VERSION_MAJOR) || __MINGW64_VERSION_MAJOR < 9
|
||||
typedef enum D3D11_FORMAT_SUPPORT2 {
|
||||
D3D11_FORMAT_SUPPORT2_UAV_ATOMIC_ADD = 0x1,
|
||||
D3D11_FORMAT_SUPPORT2_UAV_ATOMIC_BITWISE_OPS = 0x2,
|
||||
D3D11_FORMAT_SUPPORT2_UAV_ATOMIC_COMPARE_STORE_OR_COMPARE_EXCHANGE = 0x4,
|
||||
D3D11_FORMAT_SUPPORT2_UAV_ATOMIC_EXCHANGE = 0x8,
|
||||
D3D11_FORMAT_SUPPORT2_UAV_ATOMIC_SIGNED_MIN_OR_MAX = 0x10,
|
||||
D3D11_FORMAT_SUPPORT2_UAV_ATOMIC_UNSIGNED_MIN_OR_MAX = 0x20,
|
||||
D3D11_FORMAT_SUPPORT2_UAV_TYPED_LOAD = 0x40,
|
||||
D3D11_FORMAT_SUPPORT2_UAV_TYPED_STORE = 0x80,
|
||||
D3D11_FORMAT_SUPPORT2_OUTPUT_MERGER_LOGIC_OP = 0x100,
|
||||
D3D11_FORMAT_SUPPORT2_TILED = 0x200,
|
||||
D3D11_FORMAT_SUPPORT2_SHAREABLE = 0x400,
|
||||
D3D11_FORMAT_SUPPORT2_MULTIPLANE_OVERLAY = 0x4000
|
||||
} D3D11_FORMAT_SUPPORT2;
|
||||
#define D3D11_RESOURCE_MISC_TILE_POOL (0x20000)
|
||||
#define D3D11_RESOURCE_MISC_TILED (0x40000)
|
||||
#endif // !defined(__MINGW64_VERSION_MAJOR) || __MINGW64_VERSION_MAJOR < 9
|
||||
#endif // _MSC_VER
|
||||
|
@ -9,7 +9,7 @@ namespace dxvk {
|
||||
D3D11Device* pParent)
|
||||
: m_parent(pParent),
|
||||
m_device(pParent->GetDXVKDevice()),
|
||||
m_context(m_device->createContext()) {
|
||||
m_context(m_device->createContext(DxvkContextType::Supplementary)) {
|
||||
m_context->beginRecording(
|
||||
m_device->createCommandList());
|
||||
}
|
||||
@ -30,37 +30,47 @@ namespace dxvk {
|
||||
void D3D11Initializer::InitBuffer(
|
||||
D3D11Buffer* pBuffer,
|
||||
const D3D11_SUBRESOURCE_DATA* pInitialData) {
|
||||
VkMemoryPropertyFlags memFlags = pBuffer->GetBuffer()->memFlags();
|
||||
if (!(pBuffer->Desc()->MiscFlags & D3D11_RESOURCE_MISC_TILED)) {
|
||||
VkMemoryPropertyFlags memFlags = pBuffer->GetBuffer()->memFlags();
|
||||
|
||||
(memFlags & VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT)
|
||||
? InitHostVisibleBuffer(pBuffer, pInitialData)
|
||||
: InitDeviceLocalBuffer(pBuffer, pInitialData);
|
||||
(memFlags & VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT)
|
||||
? InitHostVisibleBuffer(pBuffer, pInitialData)
|
||||
: InitDeviceLocalBuffer(pBuffer, pInitialData);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void D3D11Initializer::InitTexture(
|
||||
D3D11CommonTexture* pTexture,
|
||||
const D3D11_SUBRESOURCE_DATA* pInitialData) {
|
||||
(pTexture->GetMapMode() == D3D11_COMMON_TEXTURE_MAP_MODE_DIRECT)
|
||||
? InitHostVisibleTexture(pTexture, pInitialData)
|
||||
: InitDeviceLocalTexture(pTexture, pInitialData);
|
||||
if (pTexture->Desc()->MiscFlags & D3D11_RESOURCE_MISC_TILED)
|
||||
InitTiledTexture(pTexture);
|
||||
else if (pTexture->GetMapMode() == D3D11_COMMON_TEXTURE_MAP_MODE_DIRECT)
|
||||
InitHostVisibleTexture(pTexture, pInitialData);
|
||||
else
|
||||
InitDeviceLocalTexture(pTexture, pInitialData);
|
||||
|
||||
SyncKeyedMutex(pTexture->GetInterface());
|
||||
}
|
||||
|
||||
|
||||
void D3D11Initializer::InitUavCounter(
|
||||
D3D11UnorderedAccessView* pUav) {
|
||||
auto counterBuffer = pUav->GetCounterSlice();
|
||||
auto counterView = pUav->GetCounterView();
|
||||
|
||||
if (!counterBuffer.defined())
|
||||
if (counterView == nullptr)
|
||||
return;
|
||||
|
||||
auto counterSlice = counterView->slice();
|
||||
|
||||
std::lock_guard<dxvk::mutex> lock(m_mutex);
|
||||
m_transferCommands += 1;
|
||||
|
||||
const uint32_t zero = 0;
|
||||
m_context->updateBuffer(
|
||||
counterBuffer.buffer(),
|
||||
0, sizeof(zero), &zero);
|
||||
counterSlice.buffer(),
|
||||
counterSlice.offset(),
|
||||
sizeof(zero), &zero);
|
||||
|
||||
FlushImplicit();
|
||||
}
|
||||
@ -123,7 +133,7 @@ namespace dxvk {
|
||||
auto desc = pTexture->Desc();
|
||||
|
||||
VkFormat packedFormat = m_parent->LookupPackedFormat(desc->Format, pTexture->GetFormatMode()).Format;
|
||||
auto formatInfo = imageFormatInfo(packedFormat);
|
||||
auto formatInfo = lookupFormatInfo(packedFormat);
|
||||
|
||||
if (pInitialData != nullptr && pInitialData->pSysMem != nullptr) {
|
||||
// pInitialData is an array that stores an entry for
|
||||
@ -253,6 +263,15 @@ namespace dxvk {
|
||||
}
|
||||
|
||||
|
||||
void D3D11Initializer::InitTiledTexture(
|
||||
D3D11CommonTexture* pTexture) {
|
||||
m_context->initSparseImage(pTexture->GetImage());
|
||||
|
||||
m_transferCommands += 1;
|
||||
FlushImplicit();
|
||||
}
|
||||
|
||||
|
||||
void D3D11Initializer::FlushImplicit() {
|
||||
if (m_transferCommands > MaxTransferCommands
|
||||
|| m_transferMemory > MaxTransferMemory)
|
||||
@ -261,10 +280,20 @@ namespace dxvk {
|
||||
|
||||
|
||||
void D3D11Initializer::FlushInternal() {
|
||||
m_context->flushCommandList();
|
||||
m_context->flushCommandList(nullptr);
|
||||
|
||||
m_transferCommands = 0;
|
||||
m_transferMemory = 0;
|
||||
}
|
||||
|
||||
|
||||
void D3D11Initializer::SyncKeyedMutex(ID3D11Resource *pResource) {
|
||||
Com<IDXGIKeyedMutex> keyedMutex;
|
||||
if (pResource->QueryInterface(__uuidof(IDXGIKeyedMutex), reinterpret_cast<void**>(&keyedMutex)) != S_OK)
|
||||
return;
|
||||
|
||||
keyedMutex->AcquireSync(0, 0);
|
||||
keyedMutex->ReleaseSync(0);
|
||||
}
|
||||
|
||||
}
|
@ -64,10 +64,15 @@ namespace dxvk {
|
||||
void InitHostVisibleTexture(
|
||||
D3D11CommonTexture* pTexture,
|
||||
const D3D11_SUBRESOURCE_DATA* pInitialData);
|
||||
|
||||
|
||||
void InitTiledTexture(
|
||||
D3D11CommonTexture* pTexture);
|
||||
|
||||
void FlushImplicit();
|
||||
void FlushInternal();
|
||||
|
||||
void SyncKeyedMutex(ID3D11Resource *pResource);
|
||||
|
||||
};
|
||||
|
||||
}
|
@ -46,13 +46,16 @@ namespace dxvk {
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
Logger::warn("D3D11InputLayout::QueryInterface: Unknown interface query");
|
||||
Logger::warn(str::format(riid));
|
||||
if (logQueryInterfaceError(__uuidof(ID3D11InputLayout), riid)) {
|
||||
Logger::warn("D3D11InputLayout::QueryInterface: Unknown interface query");
|
||||
Logger::warn(str::format(riid));
|
||||
}
|
||||
|
||||
return E_NOINTERFACE;
|
||||
}
|
||||
|
||||
|
||||
void D3D11InputLayout::BindToContext(const Rc<DxvkContext>& ctx) {
|
||||
void D3D11InputLayout::BindToContext(DxvkContext* ctx) {
|
||||
ctx->setInputLayout(
|
||||
m_attributes.size(),
|
||||
m_attributes.data(),
|
||||
|
@ -25,8 +25,7 @@ namespace dxvk {
|
||||
REFIID riid,
|
||||
void** ppvObject) final;
|
||||
|
||||
void BindToContext(
|
||||
const Rc<DxvkContext>& ctx);
|
||||
void BindToContext(DxvkContext* ctx);
|
||||
|
||||
bool Compare(
|
||||
const D3D11InputLayout* pOther) const;
|
||||
|
@ -28,6 +28,26 @@ enum D3D11_VK_BARRIER_CONTROL : uint32_t {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* \brief Extended shader interface
|
||||
*/
|
||||
MIDL_INTERFACE("bb8a4fb9-3935-4762-b44b-35189a26414a")
|
||||
ID3D11VkExtShader : public IUnknown {
|
||||
/**
|
||||
* \brief Retrieves SPIR-V code from a shader object
|
||||
*
|
||||
* \param [in,out] pCodeSize Shader code size, in bytes. If
|
||||
* \ref pCode is \c nullptr, this will return the total
|
||||
* code size, otherwise the number of bytes written.
|
||||
* \param [out] pCode SPIR-V shader code
|
||||
* \returns \c S_OK, or \c S_FALSE if the buffer was too small
|
||||
*/
|
||||
virtual HRESULT STDMETHODCALLTYPE GetSpirvCode(
|
||||
SIZE_T* pCodeSize,
|
||||
void* pCode) = 0;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* \brief Extended D3D11 device
|
||||
*
|
||||
@ -164,11 +184,13 @@ ID3D11VkExtContext1 : public ID3D11VkExtContext {
|
||||
|
||||
|
||||
#ifdef _MSC_VER
|
||||
struct __declspec(uuid("bb8a4fb9-3935-4762-b44b-35189a26414a")) ID3D11VkExtShader;
|
||||
struct __declspec(uuid("8a6e3c42-f74c-45b7-8265-a231b677ca17")) ID3D11VkExtDevice;
|
||||
struct __declspec(uuid("cfcf64ef-9586-46d0-bca4-97cf2ca61b06")) ID3D11VkExtDevice1;
|
||||
struct __declspec(uuid("fd0bca13-5cb6-4c3a-987e-4750de2ca791")) ID3D11VkExtContext;
|
||||
struct __declspec(uuid("874b09b2-ae0b-41d8-8476-5f3b7a0e879d")) ID3D11VkExtContext1;
|
||||
#else
|
||||
__CRT_UUID_DECL(ID3D11VkExtShader, 0xbb8a4fb9,0x3935,0x4762,0xb4,0x4b,0x35,0x18,0x9a,0x26,0x41,0x4a);
|
||||
__CRT_UUID_DECL(ID3D11VkExtDevice, 0x8a6e3c42,0xf74c,0x45b7,0x82,0x65,0xa2,0x31,0xb6,0x77,0xca,0x17);
|
||||
__CRT_UUID_DECL(ID3D11VkExtDevice1, 0xcfcf64ef,0x9586,0x46d0,0xbc,0xa4,0x97,0xcf,0x2c,0xa6,0x1b,0x06);
|
||||
__CRT_UUID_DECL(ID3D11VkExtContext, 0xfd0bca13,0x5cb6,0x4c3a,0x98,0x7e,0x47,0x50,0xde,0x2c,0xa7,0x91);
|
||||
|
@ -75,21 +75,15 @@ namespace dxvk {
|
||||
const VkImageSubresourceRange* pSubresources,
|
||||
VkImageLayout OldLayout,
|
||||
VkImageLayout NewLayout) {
|
||||
Com<ID3D11DeviceContext> deviceContext = nullptr;
|
||||
m_device->GetImmediateContext(&deviceContext);
|
||||
|
||||
auto immediateContext = static_cast<D3D11ImmediateContext*>(deviceContext.ptr());
|
||||
|
||||
auto immediateContext = m_device->GetContext();
|
||||
|
||||
immediateContext->TransitionSurfaceLayout(
|
||||
pSurface, pSubresources, OldLayout, NewLayout);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11VkInterop::FlushRenderingCommands() {
|
||||
Com<ID3D11DeviceContext> deviceContext = nullptr;
|
||||
m_device->GetImmediateContext(&deviceContext);
|
||||
|
||||
auto immediateContext = static_cast<D3D11ImmediateContext*>(deviceContext.ptr());
|
||||
auto immediateContext = m_device->GetContext();
|
||||
immediateContext->Flush();
|
||||
immediateContext->SynchronizeCsThread(DxvkCsThread::SynchronizeAll);
|
||||
}
|
||||
|
@ -15,7 +15,7 @@ namespace dxvk {
|
||||
extern "C" {
|
||||
using namespace dxvk;
|
||||
|
||||
DLLEXPORT HRESULT __stdcall D3D11CoreCreateDevice(
|
||||
HRESULT D3D11InternalCreateDevice(
|
||||
IDXGIFactory* pFactory,
|
||||
IDXGIAdapter* pAdapter,
|
||||
UINT Flags,
|
||||
@ -34,7 +34,7 @@ extern "C" {
|
||||
dxvkAdapter = dxgiVkAdapter->GetDXVKAdapter();
|
||||
dxvkInstance = dxgiVkAdapter->GetDXVKInstance();
|
||||
} else {
|
||||
Logger::warn("D3D11CoreCreateDevice: Adapter is not a DXVK adapter");
|
||||
Logger::warn("D3D11InternalCreateDevice: Adapter is not a DXVK adapter");
|
||||
DXGI_ADAPTER_DESC desc;
|
||||
pAdapter->GetDesc(&desc);
|
||||
|
||||
@ -59,40 +59,49 @@ extern "C" {
|
||||
D3D_FEATURE_LEVEL_9_2, D3D_FEATURE_LEVEL_9_1,
|
||||
};
|
||||
|
||||
if (pFeatureLevels == nullptr || FeatureLevels == 0) {
|
||||
if (!pFeatureLevels || !FeatureLevels) {
|
||||
pFeatureLevels = defaultFeatureLevels.data();
|
||||
FeatureLevels = defaultFeatureLevels.size();
|
||||
}
|
||||
|
||||
// Find the highest feature level supported by the device.
|
||||
// This works because the feature level array is ordered.
|
||||
UINT flId;
|
||||
D3D_FEATURE_LEVEL maxFeatureLevel = D3D11Device::GetMaxFeatureLevel(dxvkInstance, dxvkAdapter);
|
||||
D3D_FEATURE_LEVEL minFeatureLevel = D3D_FEATURE_LEVEL();
|
||||
D3D_FEATURE_LEVEL devFeatureLevel = D3D_FEATURE_LEVEL();
|
||||
|
||||
for (flId = 0 ; flId < FeatureLevels; flId++) {
|
||||
Logger::info(str::format("D3D11CoreCreateDevice: Probing ", pFeatureLevels[flId]));
|
||||
|
||||
if (D3D11Device::CheckFeatureLevelSupport(dxvkInstance, dxvkAdapter, pFeatureLevels[flId]))
|
||||
Logger::info(str::format("D3D11InternalCreateDevice: Maximum supported feature level: ", maxFeatureLevel));
|
||||
|
||||
for (uint32_t flId = 0 ; flId < FeatureLevels; flId++) {
|
||||
minFeatureLevel = pFeatureLevels[flId];
|
||||
|
||||
if (minFeatureLevel <= maxFeatureLevel) {
|
||||
devFeatureLevel = minFeatureLevel;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (flId == FeatureLevels) {
|
||||
Logger::err("D3D11CoreCreateDevice: Requested feature level not supported");
|
||||
|
||||
if (!devFeatureLevel) {
|
||||
Logger::err(str::format("D3D11InternalCreateDevice: Minimum required feature level ", minFeatureLevel, " not supported"));
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
|
||||
// Try to create the device with the given parameters.
|
||||
const D3D_FEATURE_LEVEL fl = pFeatureLevels[flId];
|
||||
|
||||
|
||||
try {
|
||||
Logger::info(str::format("D3D11CoreCreateDevice: Using feature level ", fl));
|
||||
Logger::info(str::format("D3D11InternalCreateDevice: Using feature level ", devFeatureLevel));
|
||||
|
||||
DxvkDeviceFeatures deviceFeatures = D3D11Device::GetDeviceFeatures(dxvkAdapter);
|
||||
Rc<DxvkDevice> dxvkDevice = dxvkAdapter->createDevice(dxvkInstance, deviceFeatures);
|
||||
|
||||
Com<D3D11DXGIDevice> device = new D3D11DXGIDevice(
|
||||
pAdapter, dxvkInstance, dxvkAdapter, fl, Flags);
|
||||
|
||||
pAdapter, nullptr, nullptr,
|
||||
dxvkInstance, dxvkAdapter, dxvkDevice,
|
||||
devFeatureLevel, Flags);
|
||||
|
||||
return device->QueryInterface(
|
||||
__uuidof(ID3D11Device),
|
||||
reinterpret_cast<void**>(ppDevice));
|
||||
} catch (const DxvkError& e) {
|
||||
Logger::err("D3D11CoreCreateDevice: Failed to create D3D11 device");
|
||||
Logger::err("D3D11InternalCreateDevice: Failed to create D3D11 device");
|
||||
return E_FAIL;
|
||||
}
|
||||
}
|
||||
@ -164,7 +173,7 @@ extern "C" {
|
||||
}
|
||||
|
||||
// Create the actual device
|
||||
hr = D3D11CoreCreateDevice(
|
||||
hr = D3D11InternalCreateDevice(
|
||||
dxgiFactory.ptr(), dxgiAdapter.ptr(),
|
||||
Flags, pFeatureLevels, FeatureLevels,
|
||||
&device);
|
||||
@ -203,6 +212,25 @@ extern "C" {
|
||||
}
|
||||
|
||||
|
||||
DLLEXPORT HRESULT __stdcall D3D11CoreCreateDevice(
|
||||
IDXGIFactory* pFactory,
|
||||
IDXGIAdapter* pAdapter,
|
||||
D3D_DRIVER_TYPE DriverType,
|
||||
HMODULE Software,
|
||||
UINT Flags,
|
||||
const D3D_FEATURE_LEVEL* pFeatureLevels,
|
||||
UINT FeatureLevels,
|
||||
UINT SDKVersion,
|
||||
ID3D11Device** ppDevice,
|
||||
D3D_FEATURE_LEVEL* pFeatureLevel) {
|
||||
return D3D11InternalCreateDeviceAndSwapChain(
|
||||
pAdapter, DriverType, Software, Flags,
|
||||
pFeatureLevels, FeatureLevels, SDKVersion,
|
||||
nullptr, nullptr,
|
||||
ppDevice, pFeatureLevel, nullptr);
|
||||
}
|
||||
|
||||
|
||||
DLLEXPORT HRESULT __stdcall D3D11CreateDevice(
|
||||
IDXGIAdapter* pAdapter,
|
||||
D3D_DRIVER_TYPE DriverType,
|
||||
@ -254,12 +282,169 @@ extern "C" {
|
||||
ID3D11Device** ppDevice,
|
||||
ID3D11DeviceContext** ppImmediateContext,
|
||||
D3D_FEATURE_LEVEL* pChosenFeatureLevel) {
|
||||
static bool s_errorShown = false;
|
||||
InitReturnPtr(ppDevice);
|
||||
InitReturnPtr(ppImmediateContext);
|
||||
|
||||
if (!std::exchange(s_errorShown, true))
|
||||
Logger::err("D3D11On12CreateDevice: Not implemented");
|
||||
if (pChosenFeatureLevel)
|
||||
*pChosenFeatureLevel = D3D_FEATURE_LEVEL(0);
|
||||
|
||||
return E_NOTIMPL;
|
||||
if (!pDevice)
|
||||
return E_INVALIDARG;
|
||||
|
||||
// Figure out D3D12 objects
|
||||
Com<ID3D12Device> d3d12Device;
|
||||
Com<ID3D12CommandQueue> d3d12Queue;
|
||||
|
||||
if (FAILED(pDevice->QueryInterface(__uuidof(ID3D12Device), reinterpret_cast<void**>(&d3d12Device)))) {
|
||||
Logger::err("D3D11On12CreateDevice: Device is not a valid D3D12 device");
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
|
||||
if (NodeMask & (NodeMask - 1)) {
|
||||
Logger::err("D3D11On12CreateDevice: Invalid node mask");
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
|
||||
if (!NumQueues || !ppCommandQueues || !ppCommandQueues[0]) {
|
||||
Logger::err("D3D11On12CreateDevice: No command queue specified");
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
|
||||
if (NumQueues > 1) {
|
||||
// Not sure what to do with more than one graphics queue
|
||||
Logger::warn("D3D11On12CreateDevice: Only one queue supported");
|
||||
}
|
||||
|
||||
if (FAILED(ppCommandQueues[0]->QueryInterface(__uuidof(ID3D12CommandQueue), reinterpret_cast<void**>(&d3d12Queue)))) {
|
||||
Logger::err("D3D11On12CreateDevice: Queue is not a valid D3D12 command queue");
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
|
||||
// Determine feature level for the D3D11 device
|
||||
std::array<D3D_FEATURE_LEVEL, 4> defaultFeatureLevels = {{
|
||||
D3D_FEATURE_LEVEL_11_0, D3D_FEATURE_LEVEL_11_1,
|
||||
D3D_FEATURE_LEVEL_12_0, D3D_FEATURE_LEVEL_12_1,
|
||||
}};
|
||||
|
||||
D3D12_FEATURE_DATA_FEATURE_LEVELS featureLevel = { };
|
||||
|
||||
if (!FeatureLevels || !pFeatureLevels) {
|
||||
featureLevel.NumFeatureLevels = defaultFeatureLevels.size();
|
||||
featureLevel.pFeatureLevelsRequested = defaultFeatureLevels.data();
|
||||
} else {
|
||||
featureLevel.NumFeatureLevels = FeatureLevels;
|
||||
featureLevel.pFeatureLevelsRequested = pFeatureLevels;
|
||||
}
|
||||
|
||||
HRESULT hr = d3d12Device->CheckFeatureSupport(D3D12_FEATURE_FEATURE_LEVELS, &featureLevel, sizeof(featureLevel));
|
||||
|
||||
if (FAILED(hr) || !featureLevel.MaxSupportedFeatureLevel) {
|
||||
Logger::err(str::format("D3D11On12CreateDevice: Minimum required feature level not supported"));
|
||||
return hr;
|
||||
}
|
||||
|
||||
Logger::info(str::format("D3D11On12CreateDevice: Chosen feature level: ", featureLevel.MaxSupportedFeatureLevel));
|
||||
|
||||
Com<ID3D12DXVKInteropDevice> interopDevice;
|
||||
|
||||
if (FAILED(d3d12Device->QueryInterface(__uuidof(ID3D12DXVKInteropDevice), reinterpret_cast<void**>(&interopDevice)))) {
|
||||
Logger::err("D3D11On12CreateDevice: Device not a vkd3d-proton device.");
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
|
||||
Com<IDXGIAdapter> dxgiAdapter;
|
||||
|
||||
if (FAILED(interopDevice->GetDXGIAdapter(IID_PPV_ARGS(&dxgiAdapter)))) {
|
||||
Logger::err("D3D11On12CreateDevice: Failed to query DXGI adapter.");
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
|
||||
try {
|
||||
// Initialize DXVK instance
|
||||
DxvkInstanceImportInfo instanceInfo = { };
|
||||
DxvkDeviceImportInfo deviceInfo = { };
|
||||
VkPhysicalDevice vulkanAdapter = VK_NULL_HANDLE;
|
||||
|
||||
interopDevice->GetVulkanHandles(&instanceInfo.instance, &vulkanAdapter, &deviceInfo.device);
|
||||
|
||||
uint32_t instanceExtensionCount = 0;
|
||||
interopDevice->GetInstanceExtensions(&instanceExtensionCount, nullptr);
|
||||
|
||||
std::vector<const char*> instanceExtensions(instanceExtensionCount);
|
||||
interopDevice->GetInstanceExtensions(&instanceExtensionCount, instanceExtensions.data());
|
||||
|
||||
instanceInfo.extensionCount = instanceExtensions.size();
|
||||
instanceInfo.extensionNames = instanceExtensions.data();
|
||||
|
||||
Rc<DxvkInstance> dxvkInstance = new DxvkInstance(instanceInfo);
|
||||
|
||||
// Find adapter by physical device handle
|
||||
Rc<DxvkAdapter> dxvkAdapter;
|
||||
|
||||
for (uint32_t i = 0; i < dxvkInstance->adapterCount(); i++) {
|
||||
Rc<DxvkAdapter> curr = dxvkInstance->enumAdapters(i);
|
||||
|
||||
if (curr->handle() == vulkanAdapter)
|
||||
dxvkAdapter = std::move(curr);
|
||||
}
|
||||
|
||||
if (dxvkAdapter == nullptr) {
|
||||
Logger::err("D3D11On12CreateDevice: No matching adapter found");
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
|
||||
interopDevice->GetVulkanQueueInfo(d3d12Queue.ptr(), &deviceInfo.queue, &deviceInfo.queueFamily);
|
||||
interopDevice->GetDeviceFeatures(&deviceInfo.features);
|
||||
|
||||
uint32_t deviceExtensionCount = 0;
|
||||
interopDevice->GetDeviceExtensions(&deviceExtensionCount, nullptr);
|
||||
|
||||
std::vector<const char*> deviceExtensions(deviceExtensionCount);
|
||||
interopDevice->GetDeviceExtensions(&deviceExtensionCount, deviceExtensions.data());
|
||||
|
||||
deviceInfo.extensionCount = deviceExtensions.size();
|
||||
deviceInfo.extensionNames = deviceExtensions.data();
|
||||
|
||||
deviceInfo.queueCallback = [
|
||||
cDevice = interopDevice,
|
||||
cQueue = d3d12Queue
|
||||
] (bool doLock) {
|
||||
HRESULT hr = doLock
|
||||
? cDevice->LockCommandQueue(cQueue.ptr())
|
||||
: cDevice->UnlockCommandQueue(cQueue.ptr());
|
||||
|
||||
if (FAILED(hr))
|
||||
Logger::err(str::format("Failed to lock vkd3d-proton device queue: ", hr));
|
||||
};
|
||||
|
||||
Rc<DxvkDevice> dxvkDevice = dxvkAdapter->importDevice(dxvkInstance, deviceInfo);
|
||||
|
||||
// Create and return the actual D3D11 device
|
||||
Com<D3D11DXGIDevice> device = new D3D11DXGIDevice(
|
||||
dxgiAdapter.ptr(), d3d12Device.ptr(), d3d12Queue.ptr(),
|
||||
dxvkInstance, dxvkAdapter, dxvkDevice,
|
||||
featureLevel.MaxSupportedFeatureLevel, Flags);
|
||||
|
||||
Com<ID3D11Device> d3d11Device;
|
||||
device->QueryInterface(__uuidof(ID3D11Device), reinterpret_cast<void**>(&d3d11Device));
|
||||
|
||||
if (ppDevice)
|
||||
*ppDevice = d3d11Device.ref();
|
||||
|
||||
if (ppImmediateContext)
|
||||
d3d11Device->GetImmediateContext(ppImmediateContext);
|
||||
|
||||
if (pChosenFeatureLevel)
|
||||
*pChosenFeatureLevel = d3d11Device->GetFeatureLevel();
|
||||
|
||||
if (!ppDevice && !ppImmediateContext)
|
||||
return S_FALSE;
|
||||
|
||||
return S_OK;
|
||||
} catch (const DxvkError& e) {
|
||||
Logger::err("D3D11On12CreateDevice: Failed to create D3D11 device");
|
||||
return E_FAIL;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
150
src/d3d11/d3d11_on_12.cpp
Normal file
150
src/d3d11/d3d11_on_12.cpp
Normal file
@ -0,0 +1,150 @@
|
||||
#include "d3d11_context_imm.h"
|
||||
#include "d3d11_device.h"
|
||||
#include "d3d11_on_12.h"
|
||||
|
||||
namespace dxvk {
|
||||
|
||||
D3D11on12Device::D3D11on12Device(
|
||||
D3D11DXGIDevice* pContainer,
|
||||
D3D11Device* pDevice,
|
||||
ID3D12Device* pD3D12Device,
|
||||
ID3D12CommandQueue* pD3D12Queue)
|
||||
: m_container (pContainer),
|
||||
m_device (pDevice),
|
||||
m_d3d12Device (pD3D12Device),
|
||||
m_d3d12Queue (pD3D12Queue) {
|
||||
|
||||
}
|
||||
|
||||
|
||||
D3D11on12Device::~D3D11on12Device() {
|
||||
|
||||
}
|
||||
|
||||
|
||||
ULONG STDMETHODCALLTYPE D3D11on12Device::AddRef() {
|
||||
return m_container->AddRef();
|
||||
}
|
||||
|
||||
|
||||
ULONG STDMETHODCALLTYPE D3D11on12Device::Release() {
|
||||
return m_container->Release();
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D11on12Device::QueryInterface(
|
||||
REFIID riid,
|
||||
void** ppvObject) {
|
||||
return m_container->QueryInterface(riid, ppvObject);
|
||||
}
|
||||
|
||||
|
||||
HRESULT STDMETHODCALLTYPE D3D11on12Device::CreateWrappedResource(
|
||||
IUnknown* pResource12,
|
||||
const D3D11_RESOURCE_FLAGS* pResourceFlags,
|
||||
D3D12_RESOURCE_STATES InputState,
|
||||
D3D12_RESOURCE_STATES OutputState,
|
||||
REFIID riid,
|
||||
void** ppResource11) {
|
||||
Com<ID3D12DXVKInteropDevice> interopDevice;
|
||||
m_d3d12Device->QueryInterface(__uuidof(ID3D12DXVKInteropDevice), reinterpret_cast<void**>(&interopDevice));
|
||||
|
||||
D3D11_ON_12_RESOURCE_INFO info = { };
|
||||
info.InputState = InputState;
|
||||
info.OutputState = OutputState;
|
||||
info.IsWrappedResource = TRUE;
|
||||
|
||||
// 11on12 technically allows importing D3D12 heaps as tile pools,
|
||||
// but we don't support importing sparse resources at this time.
|
||||
if (FAILED(pResource12->QueryInterface(__uuidof(ID3D12Resource), reinterpret_cast<void**>(&info.Resource)))) {
|
||||
Logger::err("D3D11on12Device::CreateWrappedResource: Resource not a valid D3D12 resource");
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
|
||||
// Query Vulkan resource handle and buffer offset as necessary
|
||||
if (FAILED(interopDevice->GetVulkanResourceInfo(info.Resource.ptr(), &info.VulkanHandle, &info.VulkanOffset))) {
|
||||
Logger::err("D3D11on12Device::CreateWrappedResource: Failed to retrieve Vulkan resource info");
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
|
||||
Com<ID3D11Resource> resource;
|
||||
D3D12_RESOURCE_DESC desc = info.Resource->GetDesc();
|
||||
|
||||
if (desc.Dimension == D3D12_RESOURCE_DIMENSION_BUFFER) {
|
||||
D3D11_BUFFER_DESC bufferDesc;
|
||||
|
||||
if (FAILED(D3D11Buffer::GetDescFromD3D12(info.Resource.ptr(), pResourceFlags, &bufferDesc)))
|
||||
return E_INVALIDARG;
|
||||
|
||||
resource = new D3D11Buffer(m_device, &bufferDesc, &info);
|
||||
} else {
|
||||
D3D11_COMMON_TEXTURE_DESC textureDesc;
|
||||
|
||||
if (FAILED(D3D11CommonTexture::GetDescFromD3D12(info.Resource.ptr(), pResourceFlags, &textureDesc)))
|
||||
return E_INVALIDARG;
|
||||
|
||||
switch (desc.Dimension) {
|
||||
case D3D12_RESOURCE_DIMENSION_TEXTURE1D:
|
||||
resource = new D3D11Texture1D(m_device, &textureDesc, &info);
|
||||
break;
|
||||
|
||||
case D3D12_RESOURCE_DIMENSION_TEXTURE2D:
|
||||
resource = new D3D11Texture2D(m_device, &textureDesc, &info, nullptr);
|
||||
break;
|
||||
|
||||
case D3D12_RESOURCE_DIMENSION_TEXTURE3D:
|
||||
resource = new D3D11Texture3D(m_device, &textureDesc, &info);
|
||||
break;
|
||||
|
||||
default:
|
||||
Logger::err("D3D11on12Device::CreateWrappedResource: Unhandled resource dimension");
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
}
|
||||
|
||||
return resource->QueryInterface(riid, ppResource11);
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11on12Device::ReleaseWrappedResources(
|
||||
ID3D11Resource* const* ppResources,
|
||||
UINT ResourceCount) {
|
||||
Com<ID3D12DXVKInteropDevice> interopDevice;
|
||||
m_d3d12Device->QueryInterface(__uuidof(ID3D12DXVKInteropDevice), reinterpret_cast<void**>(&interopDevice));
|
||||
|
||||
for (uint32_t i = 0; i < ResourceCount; i++) {
|
||||
D3D11_ON_12_RESOURCE_INFO info;
|
||||
|
||||
if (FAILED(GetResource11on12Info(ppResources[i], &info)) || !info.IsWrappedResource) {
|
||||
Logger::warn("D3D11on12Device::ReleaseWrappedResources: Resource not a wrapped resource, skipping");
|
||||
continue;
|
||||
}
|
||||
|
||||
VkImageLayout layout = VK_IMAGE_LAYOUT_UNDEFINED;
|
||||
interopDevice->GetVulkanImageLayout(info.Resource.ptr(), info.OutputState, &layout);
|
||||
m_device->GetContext()->Release11on12Resource(ppResources[i], layout);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void STDMETHODCALLTYPE D3D11on12Device::AcquireWrappedResources(
|
||||
ID3D11Resource* const* ppResources,
|
||||
UINT ResourceCount) {
|
||||
Com<ID3D12DXVKInteropDevice> interopDevice;
|
||||
m_d3d12Device->QueryInterface(__uuidof(ID3D12DXVKInteropDevice), reinterpret_cast<void**>(&interopDevice));
|
||||
|
||||
for (uint32_t i = 0; i < ResourceCount; i++) {
|
||||
D3D11_ON_12_RESOURCE_INFO info;
|
||||
|
||||
if (FAILED(GetResource11on12Info(ppResources[i], &info)) || !info.IsWrappedResource) {
|
||||
Logger::warn("D3D11on12Device::AcquireWrappedResources: Resource not a wrapped resource, skipping");
|
||||
continue;
|
||||
}
|
||||
|
||||
VkImageLayout layout = VK_IMAGE_LAYOUT_UNDEFINED;
|
||||
interopDevice->GetVulkanImageLayout(info.Resource.ptr(), info.InputState, &layout);
|
||||
m_device->GetContext()->Acquire11on12Resource(ppResources[i], layout);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
75
src/d3d11/d3d11_on_12.h
Normal file
75
src/d3d11/d3d11_on_12.h
Normal file
@ -0,0 +1,75 @@
|
||||
#pragma once
|
||||
|
||||
#include "d3d11_on_12_interfaces.h"
|
||||
|
||||
#include "../util/log/log.h"
|
||||
|
||||
namespace dxvk {
|
||||
|
||||
class D3D11Device;
|
||||
class D3D11DXGIDevice;
|
||||
|
||||
/**
|
||||
* \brief Resource info for 11on12 resources
|
||||
*/
|
||||
struct D3D11_ON_12_RESOURCE_INFO {
|
||||
Com<ID3D12Resource> Resource;
|
||||
UINT64 VulkanHandle = 0;
|
||||
UINT64 VulkanOffset = 0;
|
||||
BOOL IsWrappedResource = FALSE;
|
||||
D3D12_RESOURCE_STATES InputState = D3D12_RESOURCE_STATE_COMMON;
|
||||
D3D12_RESOURCE_STATES OutputState = D3D12_RESOURCE_STATE_COMMON;
|
||||
};
|
||||
|
||||
|
||||
class D3D11on12Device : public ID3D11On12Device {
|
||||
|
||||
public:
|
||||
|
||||
D3D11on12Device(
|
||||
D3D11DXGIDevice* pContainer,
|
||||
D3D11Device* pDevice,
|
||||
ID3D12Device* pD3D12Device,
|
||||
ID3D12CommandQueue* pD3D12Queue);
|
||||
|
||||
~D3D11on12Device();
|
||||
|
||||
ULONG STDMETHODCALLTYPE AddRef();
|
||||
|
||||
ULONG STDMETHODCALLTYPE Release();
|
||||
|
||||
HRESULT STDMETHODCALLTYPE QueryInterface(
|
||||
REFIID riid,
|
||||
void** ppvObject);
|
||||
|
||||
HRESULT STDMETHODCALLTYPE CreateWrappedResource(
|
||||
IUnknown* pResource12,
|
||||
const D3D11_RESOURCE_FLAGS* pResourceFlags,
|
||||
D3D12_RESOURCE_STATES InputState,
|
||||
D3D12_RESOURCE_STATES OutputState,
|
||||
REFIID riid,
|
||||
void** ppResource11);
|
||||
|
||||
void STDMETHODCALLTYPE ReleaseWrappedResources(
|
||||
ID3D11Resource* const* ppResources,
|
||||
UINT ResourceCount);
|
||||
|
||||
void STDMETHODCALLTYPE AcquireWrappedResources(
|
||||
ID3D11Resource* const* ppResources,
|
||||
UINT ResourceCount);
|
||||
|
||||
bool Is11on12Device() const {
|
||||
return m_d3d12Device != nullptr;
|
||||
}
|
||||
|
||||
private:
|
||||
|
||||
D3D11DXGIDevice* m_container;
|
||||
D3D11Device* m_device;
|
||||
|
||||
Com<ID3D12Device> m_d3d12Device;
|
||||
Com<ID3D12CommandQueue> m_d3d12Queue;
|
||||
|
||||
};
|
||||
|
||||
}
|
56
src/d3d11/d3d11_on_12_interfaces.h
Normal file
56
src/d3d11/d3d11_on_12_interfaces.h
Normal file
@ -0,0 +1,56 @@
|
||||
#pragma once
|
||||
|
||||
#include "../vulkan/vulkan_loader.h"
|
||||
|
||||
#include <d3d11on12.h>
|
||||
|
||||
MIDL_INTERFACE("39da4e09-bd1c-4198-9fae-86bbe3be41fd")
|
||||
ID3D12DXVKInteropDevice : public IUnknown {
|
||||
virtual HRESULT STDMETHODCALLTYPE GetDXGIAdapter(
|
||||
REFIID iid,
|
||||
void** ppvObject) = 0;
|
||||
|
||||
virtual HRESULT STDMETHODCALLTYPE GetInstanceExtensions(
|
||||
UINT* pExtensionCount,
|
||||
const char** ppExtensions) = 0;
|
||||
|
||||
virtual HRESULT STDMETHODCALLTYPE GetDeviceExtensions(
|
||||
UINT* pExtensionCount,
|
||||
const char** ppExtensions) = 0;
|
||||
|
||||
virtual HRESULT STDMETHODCALLTYPE GetDeviceFeatures(
|
||||
const VkPhysicalDeviceFeatures2** ppFeatures) = 0;
|
||||
|
||||
virtual HRESULT STDMETHODCALLTYPE GetVulkanHandles(
|
||||
VkInstance* pVkInstance,
|
||||
VkPhysicalDevice* pVkPhysicalDevice,
|
||||
VkDevice* pVkDevice) = 0;
|
||||
|
||||
virtual HRESULT STDMETHODCALLTYPE GetVulkanQueueInfo(
|
||||
ID3D12CommandQueue* pCommandQueue,
|
||||
VkQueue* pVkQueue,
|
||||
UINT32* pVkQueueFamily) = 0;
|
||||
|
||||
virtual void STDMETHODCALLTYPE GetVulkanImageLayout(
|
||||
ID3D12Resource* pResource,
|
||||
D3D12_RESOURCE_STATES State,
|
||||
VkImageLayout* pVkLayout) = 0;
|
||||
|
||||
virtual HRESULT STDMETHODCALLTYPE GetVulkanResourceInfo(
|
||||
ID3D12Resource* pResource,
|
||||
UINT64* pVkHandle,
|
||||
UINT64* pBufferOffset) = 0;
|
||||
|
||||
virtual HRESULT STDMETHODCALLTYPE LockCommandQueue(
|
||||
ID3D12CommandQueue* pCommandQueue) = 0;
|
||||
|
||||
virtual HRESULT STDMETHODCALLTYPE UnlockCommandQueue(
|
||||
ID3D12CommandQueue* pCommandQueue) = 0;
|
||||
|
||||
};
|
||||
|
||||
#ifdef _MSC_VER
|
||||
struct __declspec(uuid("39da4e09-bd1c-4198-9fae-86bbe3be41fd")) ID3D12DXVKInteropDevice;
|
||||
#else
|
||||
__CRT_UUID_DECL(ID3D12DXVKInteropDevice, 0x39da4e09, 0xbd1c, 0x4198, 0x9f,0xae, 0x86,0xbb,0xe3,0xbe,0x41,0xfd)
|
||||
#endif
|
@ -1,29 +1,40 @@
|
||||
#include <unordered_map>
|
||||
#include "../util/util_math.h"
|
||||
|
||||
#include "d3d11_options.h"
|
||||
|
||||
namespace dxvk {
|
||||
|
||||
D3D11Options::D3D11Options(const Config& config, const Rc<DxvkDevice>& device) {
|
||||
const DxvkDeviceInfo& devInfo = device->properties();
|
||||
static bool IsAPITracingDXGI() {
|
||||
#ifdef _WIN32
|
||||
return !!::GetModuleHandle("dxgitrace.dll");
|
||||
#else
|
||||
return false;
|
||||
#endif
|
||||
}
|
||||
|
||||
D3D11Options::D3D11Options(const Config& config, const Rc<DxvkDevice>& device) {
|
||||
this->dcSingleUseMode = config.getOption<bool>("d3d11.dcSingleUseMode", true);
|
||||
this->enableRtOutputNanFixup = config.getOption<bool>("d3d11.enableRtOutputNanFixup", false);
|
||||
this->zeroInitWorkgroupMemory = config.getOption<bool>("d3d11.zeroInitWorkgroupMemory", false);
|
||||
this->forceTgsmBarriers = config.getOption<bool>("d3d11.forceTgsmBarriers", false);
|
||||
this->forceVolatileTgsmAccess = config.getOption<bool>("d3d11.forceVolatileTgsmAccess", false);
|
||||
this->relaxedBarriers = config.getOption<bool>("d3d11.relaxedBarriers", false);
|
||||
this->ignoreGraphicsBarriers = config.getOption<bool>("d3d11.ignoreGraphicsBarriers", false);
|
||||
this->maxTessFactor = config.getOption<int32_t>("d3d11.maxTessFactor", 0);
|
||||
this->samplerAnisotropy = config.getOption<int32_t>("d3d11.samplerAnisotropy", -1);
|
||||
this->samplerLodBias = config.getOption<float>("d3d11.samplerLodBias", 0.0f);
|
||||
this->clampNegativeLodBias = config.getOption<bool>("d3d11.clampNegativeLodBias", false);
|
||||
this->invariantPosition = config.getOption<bool>("d3d11.invariantPosition", true);
|
||||
this->floatControls = config.getOption<bool>("d3d11.floatControls", true);
|
||||
this->forceSampleRateShading = config.getOption<bool>("d3d11.forceSampleRateShading", false);
|
||||
this->disableMsaa = config.getOption<bool>("d3d11.disableMsaa", false);
|
||||
this->enableContextLock = config.getOption<bool>("d3d11.enableContextLock", false);
|
||||
this->deferSurfaceCreation = config.getOption<bool>("dxgi.deferSurfaceCreation", false);
|
||||
this->numBackBuffers = config.getOption<int32_t>("dxgi.numBackBuffers", 0);
|
||||
this->maxFrameLatency = config.getOption<int32_t>("dxgi.maxFrameLatency", 0);
|
||||
this->maxFrameRate = config.getOption<int32_t>("dxgi.maxFrameRate", 0);
|
||||
this->syncInterval = config.getOption<int32_t>("dxgi.syncInterval", -1);
|
||||
this->tearFree = config.getOption<Tristate>("dxgi.tearFree", Tristate::Auto);
|
||||
|
||||
// Clamp LOD bias so that people don't abuse this in unintended ways
|
||||
this->samplerLodBias = dxvk::fclamp(this->samplerLodBias, -2.0f, 1.0f);
|
||||
|
||||
int32_t maxImplicitDiscardSize = config.getOption<int32_t>("d3d11.maxImplicitDiscardSize", 256);
|
||||
this->maxImplicitDiscardSize = maxImplicitDiscardSize >= 0
|
||||
@ -35,12 +46,9 @@ namespace dxvk {
|
||||
? VkDeviceSize(maxDynamicImageBufferSize) << 10
|
||||
: VkDeviceSize(~0ull);
|
||||
|
||||
this->constantBufferRangeCheck = config.getOption<bool>("d3d11.constantBufferRangeCheck", false)
|
||||
&& DxvkGpuVendor(devInfo.core.properties.vendorID) != DxvkGpuVendor::Amd;
|
||||
|
||||
auto cachedDynamicResources = config.getOption<std::string>("d3d11.cachedDynamicResources", std::string());
|
||||
|
||||
if (::GetModuleHandle("dxgitrace.dll")) {
|
||||
if (IsAPITracingDXGI()) {
|
||||
// apitrace reads back all mapped resources on the CPU, so
|
||||
// allocating everything in cached memory is necessary to
|
||||
// achieve acceptable performance
|
||||
@ -59,6 +67,9 @@ namespace dxvk {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Shader dump path is only available via an environment variable
|
||||
this->shaderDumpPath = env::getEnvVar("DXVK_SHADER_DUMP_PATH");
|
||||
}
|
||||
|
||||
}
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
x
Reference in New Issue
Block a user