mirror of
https://gitlab.freedesktop.org/monado/monado.git
synced 2025-01-29 01:48:31 +00:00
st/oxr: Work on D3D11
This commit is contained in:
parent
945603a8be
commit
cdb8d54ca1
|
@ -2,4 +2,4 @@
|
|||
- mr.1263
|
||||
- mr.1295
|
||||
---
|
||||
Work toward support for D3D11 client applications on Windows.
|
||||
Initial support for D3D11 client applications on Windows.
|
||||
|
|
|
@ -69,6 +69,12 @@ if(XRT_HAVE_EGL)
|
|||
target_sources(st_oxr PRIVATE oxr_session_gfx_egl.c)
|
||||
endif()
|
||||
|
||||
if(XRT_HAVE_D3D11)
|
||||
target_compile_definitions(st_oxr PRIVATE XR_USE_GRAPHICS_API_D3D11)
|
||||
target_sources(st_oxr PRIVATE oxr_session_gfx_d3d11.c oxr_swapchain_d3d11.c oxr_d3d11.cpp)
|
||||
target_link_libraries(st_oxr PRIVATE aux_d3d)
|
||||
endif()
|
||||
|
||||
if(ANDROID)
|
||||
target_compile_definitions(st_oxr PRIVATE XR_USE_PLATFORM_ANDROID)
|
||||
target_sources(st_oxr PRIVATE oxr_session_gfx_gles_android.c)
|
||||
|
|
|
@ -224,6 +224,14 @@ oxr_xrCreateVulkanDeviceKHR(XrInstance instance,
|
|||
VkResult *vulkanResult);
|
||||
#endif
|
||||
|
||||
#ifdef XR_USE_GRAPHICS_API_D3D11
|
||||
|
||||
//! OpenXR API function @ep{xrGetD3D11GraphicsRequirementsKHR}
|
||||
XRAPI_ATTR XrResult XRAPI_CALL
|
||||
oxr_xrGetD3D11GraphicsRequirementsKHR(XrInstance instance,
|
||||
XrSystemId systemId,
|
||||
XrGraphicsRequirementsD3D11KHR *graphicsRequirements);
|
||||
#endif // XR_USE_GRAPHICS_API_D3D11
|
||||
|
||||
/*
|
||||
*
|
||||
|
|
|
@ -265,6 +265,10 @@ handle_non_null(struct oxr_instance *inst, struct oxr_logger *log, const char *n
|
|||
ENTRY_IF_EXT(xrCreateVulkanInstanceKHR, KHR_vulkan_enable2);
|
||||
#endif // OXR_HAVE_KHR_vulkan_enable2
|
||||
|
||||
#ifdef OXR_HAVE_KHR_D3D11_enable
|
||||
ENTRY_IF_EXT(xrGetD3D11GraphicsRequirementsKHR, KHR_D3D11_enable);
|
||||
#endif // OXR_HAVE_KHR_D3D11_enable
|
||||
|
||||
/*
|
||||
* Not logging here because there's no need to loudly advertise
|
||||
* which extensions the loader knows about (it calls this on
|
||||
|
|
|
@ -417,3 +417,30 @@ oxr_xrCreateVulkanDeviceKHR(XrInstance instance,
|
|||
return oxr_vk_create_vulkan_device(&log, sys, createInfo, vulkanDevice, vulkanResult);
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
/*
|
||||
*
|
||||
* D3D11
|
||||
*
|
||||
*/
|
||||
|
||||
#ifdef XR_USE_GRAPHICS_API_D3D11
|
||||
|
||||
XrResult
|
||||
oxr_xrGetD3D11GraphicsRequirementsKHR(XrInstance instance,
|
||||
XrSystemId systemId,
|
||||
XrGraphicsRequirementsD3D11KHR *graphicsRequirements)
|
||||
{
|
||||
|
||||
struct oxr_instance *inst;
|
||||
struct oxr_logger log;
|
||||
OXR_VERIFY_INSTANCE_AND_INIT_LOG(&log, instance, inst, "xrGetD3D11GraphicsRequirementsKHR");
|
||||
OXR_VERIFY_ARG_TYPE_AND_NOT_NULL(&log, graphicsRequirements, XR_TYPE_GRAPHICS_REQUIREMENTS_D3D11_KHR);
|
||||
OXR_VERIFY_SYSTEM_AND_GET(&log, inst, systemId, sys);
|
||||
|
||||
sys->gotten_requirements = true;
|
||||
|
||||
return oxr_d3d11_get_requirements(&log, sys, graphicsRequirements);
|
||||
}
|
||||
#endif
|
||||
|
|
|
@ -276,6 +276,10 @@ oxr_verify_XrGraphicsBindingOpenGLESAndroidKHR(struct oxr_logger *, const XrGrap
|
|||
#endif // defined(XR_USE_PLATFORM_ANDROID) &&
|
||||
// defined(XR_USE_GRAPHICS_API_OPENGL_ES)
|
||||
|
||||
#if defined(XR_USE_GRAPHICS_API_D3D11)
|
||||
XrResult
|
||||
oxr_verify_XrGraphicsBindingD3D11KHR(struct oxr_logger *, const XrGraphicsBindingD3D11KHR *);
|
||||
#endif // defined(XR_USE_GRAPHICS_API_D3D11)
|
||||
/*!
|
||||
* @}
|
||||
*/
|
||||
|
|
92
src/xrt/state_trackers/oxr/oxr_d3d11.cpp
Normal file
92
src/xrt/state_trackers/oxr/oxr_d3d11.cpp
Normal file
|
@ -0,0 +1,92 @@
|
|||
// Copyright 2021, Collabora, Ltd.
|
||||
// SPDX-License-Identifier: BSL-1.0
|
||||
/*!
|
||||
* @file
|
||||
* @brief Holds D3D11 related functions that didn't fit somewhere else.
|
||||
* @author Ryan Pavlik <ryan.pavlik@collabora.com>
|
||||
* @ingroup oxr_main
|
||||
*/
|
||||
|
||||
#include "xrt/xrt_gfx_d3d11.h"
|
||||
|
||||
#include "util/u_misc.h"
|
||||
#include "util/u_debug.h"
|
||||
#include "d3d/d3d_helpers.hpp"
|
||||
|
||||
#include "oxr_objects.h"
|
||||
#include "oxr_logger.h"
|
||||
|
||||
#include <dxgi1_6.h>
|
||||
#include <d3d11_4.h>
|
||||
#include <wil/com.h>
|
||||
#include <wil/result.h>
|
||||
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#define DEFAULT_CATCH(MSG) \
|
||||
catch (wil::ResultException const &e) \
|
||||
{ \
|
||||
return oxr_error(log, XR_ERROR_RUNTIME_FAILURE, MSG ": %s", e.what()); \
|
||||
} \
|
||||
catch (std::exception const &e) \
|
||||
{ \
|
||||
return oxr_error(log, XR_ERROR_RUNTIME_FAILURE, MSG ": %s", e.what()); \
|
||||
} \
|
||||
catch (...) \
|
||||
{ \
|
||||
return oxr_error(log, XR_ERROR_RUNTIME_FAILURE, MSG); \
|
||||
}
|
||||
|
||||
using namespace xrt::auxiliary::d3d;
|
||||
|
||||
XrResult
|
||||
oxr_d3d11_get_requirements(struct oxr_logger *log,
|
||||
struct oxr_system *sys,
|
||||
XrGraphicsRequirementsD3D11KHR *graphicsRequirements)
|
||||
{
|
||||
try {
|
||||
|
||||
if (sys->xsysc->info.client_d3d_deviceLUID_valid) {
|
||||
sys->suggested_d3d_luid =
|
||||
reinterpret_cast<const LUID &>(sys->xsysc->info.client_d3d_deviceLUID);
|
||||
} else {
|
||||
auto adapter = getAdapterByIndex(0, U_LOGGING_INFO);
|
||||
if (adapter == nullptr) {
|
||||
return oxr_error(log, XR_ERROR_RUNTIME_FAILURE, " failure enumerating adapter LUIDs.");
|
||||
}
|
||||
DXGI_ADAPTER_DESC desc{};
|
||||
THROW_IF_FAILED(adapter->GetDesc(&desc));
|
||||
sys->suggested_d3d_luid = desc.AdapterLuid;
|
||||
}
|
||||
sys->suggested_d3d_luid_valid = true;
|
||||
graphicsRequirements->adapterLuid = sys->suggested_d3d_luid;
|
||||
//! @todo implement better?
|
||||
graphicsRequirements->minFeatureLevel = D3D_FEATURE_LEVEL_11_0;
|
||||
|
||||
return XR_SUCCESS;
|
||||
}
|
||||
DEFAULT_CATCH(" failure determining adapter LUID")
|
||||
}
|
||||
|
||||
XrResult
|
||||
oxr_d3d11_check_device(struct oxr_logger *log, struct oxr_system *sys, ID3D11Device *device)
|
||||
{
|
||||
try {
|
||||
wil::com_ptr<IDXGIDevice> dxgiDevice;
|
||||
THROW_IF_FAILED(device->QueryInterface(dxgiDevice.put()));
|
||||
wil::com_ptr<IDXGIAdapter> adapter;
|
||||
THROW_IF_FAILED(dxgiDevice->GetAdapter(adapter.put()));
|
||||
DXGI_ADAPTER_DESC desc{};
|
||||
adapter->GetDesc(&desc);
|
||||
if (desc.AdapterLuid.HighPart != sys->suggested_d3d_luid.HighPart ||
|
||||
desc.AdapterLuid.LowPart != sys->suggested_d3d_luid.LowPart) {
|
||||
|
||||
return oxr_error(log, XR_ERROR_GRAPHICS_DEVICE_INVALID,
|
||||
" supplied device does not match required LUID.");
|
||||
}
|
||||
return XR_SUCCESS;
|
||||
}
|
||||
DEFAULT_CATCH(" failure checking adapter LUID")
|
||||
}
|
|
@ -1110,6 +1110,42 @@ oxr_session_populate_egl(struct oxr_logger *log,
|
|||
#endif
|
||||
|
||||
|
||||
/*
|
||||
*
|
||||
* D3D11, located in various files.
|
||||
*
|
||||
*/
|
||||
|
||||
#ifdef XR_USE_GRAPHICS_API_D3D11
|
||||
|
||||
XrResult
|
||||
oxr_d3d11_get_requirements(struct oxr_logger *log,
|
||||
struct oxr_system *sys,
|
||||
XrGraphicsRequirementsD3D11KHR *graphicsRequirements);
|
||||
|
||||
/**
|
||||
* @brief Check to ensure the device provided at session create matches the LUID we returned earlier.
|
||||
*
|
||||
* @return XR_SUCCESS if the device matches the LUID
|
||||
*/
|
||||
XrResult
|
||||
oxr_d3d11_check_device(struct oxr_logger *log, struct oxr_system *sys, ID3D11Device *device);
|
||||
|
||||
|
||||
XrResult
|
||||
oxr_session_populate_d3d11(struct oxr_logger *log,
|
||||
struct oxr_system *sys,
|
||||
XrGraphicsBindingD3D11KHR const *next,
|
||||
struct oxr_session *sess);
|
||||
|
||||
XrResult
|
||||
oxr_swapchain_d3d11_create(struct oxr_logger *,
|
||||
struct oxr_session *sess,
|
||||
const XrSwapchainCreateInfo *,
|
||||
struct oxr_swapchain **out_swapchain);
|
||||
|
||||
#endif
|
||||
|
||||
/*
|
||||
*
|
||||
* Structs
|
||||
|
@ -1205,6 +1241,10 @@ struct oxr_system
|
|||
} vk;
|
||||
|
||||
#endif
|
||||
#ifdef XR_USE_GRAPHICS_API_D3D11
|
||||
LUID suggested_d3d_luid;
|
||||
bool suggested_d3d_luid_valid;
|
||||
#endif
|
||||
};
|
||||
|
||||
#define GET_XDEV_BY_ROLE(SYS, ROLE) ((SYS)->xsysd->roles.ROLE)
|
||||
|
@ -1219,6 +1259,7 @@ struct oxr_extension_status
|
|||
{
|
||||
OXR_EXTENSION_SUPPORT_GENERATE(MAKE_EXT_STATUS)
|
||||
};
|
||||
#undef MAKE_EXT_STATUS
|
||||
|
||||
/*!
|
||||
* Main object that ties everything together.
|
||||
|
|
|
@ -734,6 +734,28 @@ oxr_session_create_impl(struct oxr_logger *log,
|
|||
}
|
||||
#endif
|
||||
|
||||
#ifdef XR_USE_GRAPHICS_API_D3D11
|
||||
XrGraphicsBindingD3D11KHR const *d3d11 =
|
||||
OXR_GET_INPUT_FROM_CHAIN(createInfo, XR_TYPE_GRAPHICS_BINDING_D3D11_KHR, XrGraphicsBindingD3D11KHR);
|
||||
if (d3d11 != NULL) {
|
||||
OXR_VERIFY_ARG_NOT_NULL(log, d3d11->device);
|
||||
|
||||
if (!sys->gotten_requirements) {
|
||||
return oxr_error(log, XR_ERROR_GRAPHICS_REQUIREMENTS_CALL_MISSING,
|
||||
"Has not called xrGetD3D11GraphicsRequirementsKHR");
|
||||
}
|
||||
XrResult result = oxr_d3d11_check_device(log, sys, d3d11->device);
|
||||
|
||||
if (!XR_SUCCEEDED(result)) {
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
OXR_SESSION_ALLOCATE(log, sys, *out_session);
|
||||
OXR_ALLOCATE_NATIVE_COMPOSITOR(log, xsi, *out_session);
|
||||
return oxr_session_populate_d3d11(log, sys, d3d11, *out_session);
|
||||
}
|
||||
#endif
|
||||
/*
|
||||
* Add any new graphics binding structs here - before the headless
|
||||
* check. (order for non-headless checks not specified in standard.)
|
||||
|
|
44
src/xrt/state_trackers/oxr/oxr_session_gfx_d3d11.c
Normal file
44
src/xrt/state_trackers/oxr/oxr_session_gfx_d3d11.c
Normal file
|
@ -0,0 +1,44 @@
|
|||
// Copyright 2018-2021, Collabora, Ltd.
|
||||
// SPDX-License-Identifier: BSL-1.0
|
||||
/*!
|
||||
* @file
|
||||
* @brief Holds D3D11 specific session functions.
|
||||
* @author Ryan Pavlik <ryan.pavlik@collabora.com>
|
||||
* @author Jakob Bornecrantz <jakob@collabora.com>
|
||||
* @ingroup oxr_main
|
||||
* @ingroup comp_client
|
||||
*/
|
||||
|
||||
#include <stdlib.h>
|
||||
|
||||
#include "util/u_misc.h"
|
||||
|
||||
#include "xrt/xrt_instance.h"
|
||||
#include "xrt/xrt_gfx_d3d11.h"
|
||||
|
||||
#include "oxr_objects.h"
|
||||
#include "oxr_logger.h"
|
||||
#include "oxr_two_call.h"
|
||||
#include "oxr_handle.h"
|
||||
|
||||
|
||||
XrResult
|
||||
oxr_session_populate_d3d11(struct oxr_logger *log,
|
||||
struct oxr_system *sys,
|
||||
XrGraphicsBindingD3D11KHR const *next,
|
||||
struct oxr_session *sess)
|
||||
{
|
||||
struct xrt_compositor_native *xcn = sess->xcn;
|
||||
struct xrt_compositor_d3d11 *xcd3d = xrt_gfx_d3d11_provider_create( //
|
||||
xcn, //
|
||||
next->device); //
|
||||
|
||||
if (xcd3d == NULL) {
|
||||
return oxr_error(log, XR_ERROR_INITIALIZATION_FAILED, "Failed to create a d3d11 client compositor");
|
||||
}
|
||||
|
||||
sess->compositor = &xcd3d->base;
|
||||
sess->create_swapchain = oxr_swapchain_d3d11_create;
|
||||
|
||||
return XR_SUCCESS;
|
||||
}
|
78
src/xrt/state_trackers/oxr/oxr_swapchain_d3d11.c
Normal file
78
src/xrt/state_trackers/oxr/oxr_swapchain_d3d11.c
Normal file
|
@ -0,0 +1,78 @@
|
|||
// Copyright 2019-2021, Collabora, Ltd.
|
||||
// SPDX-License-Identifier: BSL-1.0
|
||||
/*!
|
||||
* @file
|
||||
* @brief Holds D3D11 swapchain related functions.
|
||||
* @author Ryan Pavlik <ryan.pavlik@collabora.com>
|
||||
* @author Jakob Bornecrantz <jakob@collabora.com>
|
||||
* @ingroup oxr_main
|
||||
* @ingroup comp_client
|
||||
*/
|
||||
|
||||
#include <stdlib.h>
|
||||
|
||||
#include "xrt/xrt_gfx_d3d11.h"
|
||||
#include "util/u_debug.h"
|
||||
|
||||
#include "oxr_objects.h"
|
||||
#include "oxr_logger.h"
|
||||
|
||||
|
||||
static XrResult
|
||||
oxr_swapchain_d3d11_destroy(struct oxr_logger *log, struct oxr_swapchain *sc)
|
||||
{
|
||||
// Release any waited image.
|
||||
if (sc->waited.yes) {
|
||||
sc->release_image(log, sc, NULL);
|
||||
}
|
||||
|
||||
// Release any acquired images.
|
||||
XrSwapchainImageWaitInfo waitInfo = {0};
|
||||
while (!u_index_fifo_is_empty(&sc->acquired.fifo)) {
|
||||
sc->wait_image(log, sc, &waitInfo);
|
||||
sc->release_image(log, sc, NULL);
|
||||
}
|
||||
|
||||
// Drop our reference, does NULL checking.
|
||||
xrt_swapchain_reference(&sc->swapchain, NULL);
|
||||
|
||||
return XR_SUCCESS;
|
||||
}
|
||||
|
||||
static XrResult
|
||||
oxr_swapchain_d3d11_enumerate_images(struct oxr_logger *log,
|
||||
struct oxr_swapchain *sc,
|
||||
uint32_t count,
|
||||
XrSwapchainImageBaseHeader *images)
|
||||
{
|
||||
struct xrt_swapchain_d3d11 *xscd3d = (struct xrt_swapchain_d3d11 *)sc->swapchain;
|
||||
XrSwapchainImageD3D11KHR *d3d_imgs = (XrSwapchainImageD3D11KHR *)images;
|
||||
|
||||
for (uint32_t i = 0; i < count; i++) {
|
||||
d3d_imgs[i].texture = xscd3d->images[i];
|
||||
}
|
||||
|
||||
return oxr_session_success_result(sc->sess);
|
||||
}
|
||||
|
||||
XrResult
|
||||
oxr_swapchain_d3d11_create(struct oxr_logger *log,
|
||||
struct oxr_session *sess,
|
||||
const XrSwapchainCreateInfo *createInfo,
|
||||
struct oxr_swapchain **out_swapchain)
|
||||
{
|
||||
struct oxr_swapchain *sc;
|
||||
XrResult ret;
|
||||
|
||||
ret = oxr_create_swapchain(log, sess, createInfo, &sc);
|
||||
if (ret != XR_SUCCESS) {
|
||||
return ret;
|
||||
}
|
||||
|
||||
sc->destroy = oxr_swapchain_d3d11_destroy;
|
||||
sc->enumerate_images = oxr_swapchain_d3d11_enumerate_images;
|
||||
|
||||
*out_swapchain = sc;
|
||||
|
||||
return XR_SUCCESS;
|
||||
}
|
|
@ -103,6 +103,10 @@ oxr_system_fill_in(struct oxr_logger *log, struct oxr_instance *inst, XrSystemId
|
|||
sys->vulkan_enable2_instance = VK_NULL_HANDLE;
|
||||
sys->suggested_vulkan_physical_device = VK_NULL_HANDLE;
|
||||
#endif
|
||||
#ifdef XR_USE_GRAPHICS_API_D3D11
|
||||
U_ZERO(&(sys->suggested_d3d_luid));
|
||||
sys->suggested_d3d_luid_valid = false;
|
||||
#endif
|
||||
|
||||
// Headless.
|
||||
if (sys->xsysc == NULL) {
|
||||
|
|
|
@ -494,6 +494,15 @@ oxr_verify_XrSessionCreateInfo(struct oxr_logger *log,
|
|||
}
|
||||
#endif // defined(XR_USE_PLATFORM_ANDROID) && defined(XR_USE_GRAPHICS_API_OPENGL_ES)
|
||||
|
||||
#if defined(XR_USE_GRAPHICS_API_D3D11)
|
||||
XrGraphicsBindingD3D11KHR const *d3d11 =
|
||||
OXR_GET_INPUT_FROM_CHAIN(createInfo, XR_TYPE_GRAPHICS_BINDING_D3D11_KHR, XrGraphicsBindingD3D11KHR);
|
||||
if (d3d11 != NULL) {
|
||||
OXR_VERIFY_EXTENSION(log, inst, KHR_D3D11_enable);
|
||||
return oxr_verify_XrGraphicsBindingD3D11KHR(log, d3d11);
|
||||
}
|
||||
#endif // XR_USE_GRAPHICS_API_D3D11
|
||||
|
||||
/*
|
||||
* Add any new graphics binding structs here - before the headless
|
||||
* check. (order for non-headless checks not specified in standard.)
|
||||
|
@ -603,3 +612,17 @@ oxr_verify_XrGraphicsBindingOpenGLESAndroidKHR(struct oxr_logger *log, const XrG
|
|||
}
|
||||
#endif // defined(XR_USE_PLATFORM_ANDROID) &&
|
||||
// defined(XR_USE_GRAPHICS_API_OPENGL_ES)
|
||||
|
||||
#if defined(XR_USE_GRAPHICS_API_D3D11)
|
||||
XrResult
|
||||
oxr_verify_XrGraphicsBindingD3D11KHR(struct oxr_logger *log, const XrGraphicsBindingD3D11KHR *next)
|
||||
{
|
||||
if (next->type != XR_TYPE_GRAPHICS_BINDING_D3D11_KHR) {
|
||||
return oxr_error(log, XR_ERROR_VALIDATION_FAILURE, "Graphics binding has invalid type");
|
||||
}
|
||||
if (next->device == NULL) {
|
||||
return oxr_error(log, XR_ERROR_VALIDATION_FAILURE, "XrGraphicsBindingD3D11KHR::device cannot be NULL");
|
||||
}
|
||||
return XR_SUCCESS;
|
||||
}
|
||||
#endif // defined(XR_USE_GRAPHICS_API_D3D11)
|
||||
|
|
Loading…
Reference in a new issue