diff --git a/vrclient_x64/gen_wrapper.py b/vrclient_x64/gen_wrapper.py index 5d3a41a5..9b5f4db0 100755 --- a/vrclient_x64/gen_wrapper.py +++ b/vrclient_x64/gen_wrapper.py @@ -5,7 +5,7 @@ from __future__ import print_function -CLANG_PATH='/usr/lib/clang/8.0.1' +CLANG_PATH='/usr/lib/clang/9.0.1' import pprint import sys @@ -297,6 +297,14 @@ def ivrcompositor_wait_get_poses(cppname, method): def ivrcompositor_get_vulkan_device_extensions_required(cppname, method): return "ivrcompositor_get_vulkan_device_extensions_required" +def ivrrendermodels_load_texture_d3d11_async(cppname, method): + assert "004" in cppname or "005" in cppname or "006" in cppname + return "ivrrendermodels_load_texture_d3d11_async" + +def ivrrendermodels_free_texture_d3d11(cppname, method): + assert "004" in cppname or "005" in cppname or "006" in cppname + return "ivrrendermodels_free_texture_d3d11" + def ivrrendermodels_load_into_texture_d3d11_async(cppname, method): assert "005" in cppname or "006" in cppname return "ivrrendermodels_load_into_texture_d3d11_async" @@ -311,6 +319,8 @@ method_overrides = [ ("IVRCompositor", "PostPresentHandoff", ivrcompositor_post_present_handoff), ("IVRCompositor", "WaitGetPoses", ivrcompositor_wait_get_poses), ("IVRCompositor", "GetVulkanDeviceExtensionsRequired", ivrcompositor_get_vulkan_device_extensions_required), + ("IVRRenderModels", "LoadTextureD3D11_Async", ivrrendermodels_load_texture_d3d11_async), + ("IVRRenderModels", "FreeTextureD3D11", ivrrendermodels_free_texture_d3d11), ("IVRRenderModels", "LoadIntoTextureD3D11_Async", ivrrendermodels_load_into_texture_d3d11_async), ] diff --git a/vrclient_x64/vrclient_x64/vrclient_defs.h b/vrclient_x64/vrclient_x64/vrclient_defs.h index 535a8d38..51d1d9ea 100644 --- a/vrclient_x64/vrclient_x64/vrclient_defs.h +++ b/vrclient_x64/vrclient_x64/vrclient_defs.h @@ -298,6 +298,7 @@ typedef enum EVRRenderModelError VRRenderModelError_None = 0, VRRenderModelError_Loading = 100, VRRenderModelError_NotSupported = 200, + VRRenderModelError_InvalidTexture = 400, } EVRRenderModelError; #endif diff --git a/vrclient_x64/vrclient_x64/vrclient_main.c b/vrclient_x64/vrclient_x64/vrclient_main.c index 0553e287..89a27c28 100644 --- a/vrclient_x64/vrclient_x64/vrclient_main.c +++ b/vrclient_x64/vrclient_x64/vrclient_main.c @@ -28,10 +28,17 @@ #include "cppIVRCompositor_IVRCompositor_021.h" #include "cppIVRCompositor_IVRCompositor_022.h" +/* 0918 is binary compatible with 1015 */ +typedef struct winRenderModel_t_0918 winRenderModel_t_0918; +typedef struct winRenderModel_TextureMap_t_0918 winRenderModel_TextureMap_t_0918; +#include "cppIVRRenderModels_IVRRenderModels_004.h" + typedef struct winRenderModel_t_1015 winRenderModel_t_1015; typedef struct winRenderModel_TextureMap_t_1015 winRenderModel_TextureMap_t_1015; #include "cppIVRRenderModels_IVRRenderModels_005.h" +/* this is cast to 1015 during load_linux_texture_map, so ensure they're + * binary compatible before updating this number */ typedef struct winRenderModel_t_1610 winRenderModel_t_1610; typedef struct winRenderModel_TextureMap_t_1610 winRenderModel_TextureMap_t_1610; #include "cppIVRRenderModels_IVRRenderModels_006.h" @@ -1097,6 +1104,108 @@ static EVRRenderModelError load_into_texture_d3d11(ID3D11Texture2D *texture, return VRRenderModelError_None; } +static EVRRenderModelError load_linux_texture_map(void *linux_side, TextureID_t texture_id, + struct winRenderModel_TextureMap_t_1015 **texture_map, unsigned int version) +{ + switch(version){ + case 4: + return cppIVRRenderModels_IVRRenderModels_004_LoadTexture_Async(linux_side, texture_id, (struct winRenderModel_TextureMap_t_0918 **)texture_map); + case 5: + return cppIVRRenderModels_IVRRenderModels_005_LoadTexture_Async(linux_side, texture_id, texture_map); + case 6: + return cppIVRRenderModels_IVRRenderModels_006_LoadTexture_Async(linux_side, texture_id, (struct winRenderModel_TextureMap_t_1610 **)texture_map); + } + FIXME("Unsupported IVRRenderModels version! %u\n", version); + return VRRenderModelError_NotSupported; +} + +static void free_linux_texture_map(void *linux_side, + struct winRenderModel_TextureMap_t_1015 *texture_map, unsigned int version) +{ + switch(version){ + case 4: + cppIVRRenderModels_IVRRenderModels_004_FreeTexture(linux_side, (struct winRenderModel_TextureMap_t_0918 *)texture_map); + break; + case 5: + cppIVRRenderModels_IVRRenderModels_005_FreeTexture(linux_side, texture_map); + break; + case 6: + cppIVRRenderModels_IVRRenderModels_006_FreeTexture(linux_side, (struct winRenderModel_TextureMap_t_1610 *)texture_map); + break; + default: + FIXME("Unsupported IVRRenderModels version! %u\n", version); + break; + } +} + +EVRRenderModelError ivrrendermodels_load_texture_d3d11_async( + EVRRenderModelError (*cpp_func)(void *, TextureID_t, void *, void **), + void *linux_side, TextureID_t texture_id, void *device, + void **dst_texture, unsigned int version) +{ + struct winRenderModel_TextureMap_t_1015 *texture_map; + EVRRenderModelError error; + D3D11_TEXTURE2D_DESC desc; + ID3D11Device *d3d11_device = device; + ID3D11Texture2D *texture; + HRESULT hr; + + error = load_linux_texture_map(linux_side, texture_id, &texture_map, version); + if (error == VRRenderModelError_Loading) + { + TRACE("Loading.\n"); + return error; + } + if (error != VRRenderModelError_None) + { + WARN("Failed to load texture %#x.\n", error); + return error; + } + + desc.Width = texture_map->unWidth; + desc.Height = texture_map->unHeight; + desc.MipLevels = 1; + desc.ArraySize = 1; + desc.Format = DXGI_FORMAT_R8G8B8A8_UNORM_SRGB; + desc.SampleDesc.Count = 1; + desc.SampleDesc.Quality = 0; + desc.Usage = D3D11_USAGE_DEFAULT; + desc.BindFlags = D3D11_BIND_SHADER_RESOURCE; + desc.CPUAccessFlags = 0; + desc.MiscFlags = 0; + + hr = d3d11_device->lpVtbl->CreateTexture2D(d3d11_device, &desc, NULL, &texture); + if (FAILED(hr)) + { + WARN("Failed to create D3D11 texture %#x\n", hr); + free_linux_texture_map(linux_side, texture_map, version); + return VRRenderModelError_InvalidTexture; + } + + error = load_into_texture_d3d11(texture, texture_map); + if (error == VRRenderModelError_None) + { + *dst_texture = texture; + } + else + { + texture->lpVtbl->Release(texture); + *dst_texture = NULL; + } + + free_linux_texture_map(linux_side, texture_map, version); + + return error; +} + +void ivrrendermodels_free_texture_d3d11( + void (*cpp_func)(void *, void *), + void *linux_side, void *dst_texture, unsigned int version) +{ + ID3D11Texture2D *d3d11_texture = dst_texture; + d3d11_texture->lpVtbl->Release(d3d11_texture); +} + EVRRenderModelError ivrrendermodels_load_into_texture_d3d11_async( EVRRenderModelError (*cpp_func)(void *, TextureID_t, void *), void *linux_side, TextureID_t texture_id, void *dst_texture, unsigned int version) @@ -1106,14 +1215,7 @@ EVRRenderModelError ivrrendermodels_load_into_texture_d3d11_async( EVRRenderModelError error; ID3D11Texture2D *texture; - switch(version){ - case 5: - error = cppIVRRenderModels_IVRRenderModels_005_LoadTexture_Async(linux_side, texture_id, &texture_map); - break; - case 6: - error = cppIVRRenderModels_IVRRenderModels_006_LoadTexture_Async(linux_side, texture_id, (struct winRenderModel_TextureMap_t_1610 **)&texture_map); - break; - } + error = load_linux_texture_map(linux_side, texture_id, &texture_map, version); if (error == VRRenderModelError_Loading) { TRACE("Loading.\n"); @@ -1136,14 +1238,8 @@ EVRRenderModelError ivrrendermodels_load_into_texture_d3d11_async( error = VRRenderModelError_NotSupported; } - switch(version){ - case 5: - cppIVRRenderModels_IVRRenderModels_005_FreeTexture(linux_side, texture_map); - break; - case 6: - cppIVRRenderModels_IVRRenderModels_006_FreeTexture(linux_side, (struct winRenderModel_TextureMap_t_1610 *)texture_map); - break; - } + free_linux_texture_map(linux_side, texture_map, version); + return error; } diff --git a/vrclient_x64/vrclient_x64/vrclient_private.h b/vrclient_x64/vrclient_x64/vrclient_private.h index 93b3ac06..e7fe066a 100644 --- a/vrclient_x64/vrclient_x64/vrclient_private.h +++ b/vrclient_x64/vrclient_x64/vrclient_private.h @@ -135,9 +135,15 @@ uint32_t ivrcompositor_get_vulkan_device_extensions_required( void *linux_side, VkPhysicalDevice_T *phys_dev, char *value, uint32_t bufsize, unsigned int version, struct compositor_data *user_data); +EVRRenderModelError ivrrendermodels_load_texture_d3d11_async( + EVRRenderModelError (*cpp_func)(void *, TextureID_t, void *, void **), + void *linux_side, TextureID_t texture_id, void *d3d11_device, void **dst_texture, unsigned int version); EVRRenderModelError ivrrendermodels_load_into_texture_d3d11_async( EVRRenderModelError (*cpp_func)(void *, TextureID_t, void *), void *linux_side, TextureID_t texture_id, void *dst_texture, unsigned int version); +void ivrrendermodels_free_texture_d3d11( + void (*cpp_func)(void *, void *), + void *linux_side, void *dst_texture, unsigned int version); #endif /* __cplusplus */ diff --git a/vrclient_x64/vrclient_x64/winIVRRenderModels.c b/vrclient_x64/vrclient_x64/winIVRRenderModels.c index 8bb5640f..38c7bae9 100644 --- a/vrclient_x64/vrclient_x64/winIVRRenderModels.c +++ b/vrclient_x64/vrclient_x64/winIVRRenderModels.c @@ -57,7 +57,7 @@ DEFINE_THISCALL_WRAPPER(winIVRRenderModels_IVRRenderModels_006_LoadTextureD3D11_ EVRRenderModelError __thiscall winIVRRenderModels_IVRRenderModels_006_LoadTextureD3D11_Async(winIVRRenderModels_IVRRenderModels_006 *_this, TextureID_t textureId, void * pD3D11Device, void ** ppD3D11Texture2D) { TRACE("%p\n", _this); - return cppIVRRenderModels_IVRRenderModels_006_LoadTextureD3D11_Async(_this->linux_side, textureId, pD3D11Device, ppD3D11Texture2D); + return ivrrendermodels_load_texture_d3d11_async(cppIVRRenderModels_IVRRenderModels_006_LoadTextureD3D11_Async, _this->linux_side, textureId, pD3D11Device, ppD3D11Texture2D, 6); } DEFINE_THISCALL_WRAPPER(winIVRRenderModels_IVRRenderModels_006_LoadIntoTextureD3D11_Async, 12) @@ -71,7 +71,7 @@ DEFINE_THISCALL_WRAPPER(winIVRRenderModels_IVRRenderModels_006_FreeTextureD3D11, void __thiscall winIVRRenderModels_IVRRenderModels_006_FreeTextureD3D11(winIVRRenderModels_IVRRenderModels_006 *_this, void * pD3D11Texture2D) { TRACE("%p\n", _this); - cppIVRRenderModels_IVRRenderModels_006_FreeTextureD3D11(_this->linux_side, pD3D11Texture2D); + ivrrendermodels_free_texture_d3d11(cppIVRRenderModels_IVRRenderModels_006_FreeTextureD3D11, _this->linux_side, pD3D11Texture2D, 6); } DEFINE_THISCALL_WRAPPER(winIVRRenderModels_IVRRenderModels_006_GetRenderModelName, 16) @@ -285,7 +285,7 @@ DEFINE_THISCALL_WRAPPER(winIVRRenderModels_IVRRenderModels_005_LoadTextureD3D11_ EVRRenderModelError __thiscall winIVRRenderModels_IVRRenderModels_005_LoadTextureD3D11_Async(winIVRRenderModels_IVRRenderModels_005 *_this, TextureID_t textureId, void * pD3D11Device, void ** ppD3D11Texture2D) { TRACE("%p\n", _this); - return cppIVRRenderModels_IVRRenderModels_005_LoadTextureD3D11_Async(_this->linux_side, textureId, pD3D11Device, ppD3D11Texture2D); + return ivrrendermodels_load_texture_d3d11_async(cppIVRRenderModels_IVRRenderModels_005_LoadTextureD3D11_Async, _this->linux_side, textureId, pD3D11Device, ppD3D11Texture2D, 5); } DEFINE_THISCALL_WRAPPER(winIVRRenderModels_IVRRenderModels_005_LoadIntoTextureD3D11_Async, 12) @@ -299,7 +299,7 @@ DEFINE_THISCALL_WRAPPER(winIVRRenderModels_IVRRenderModels_005_FreeTextureD3D11, void __thiscall winIVRRenderModels_IVRRenderModels_005_FreeTextureD3D11(winIVRRenderModels_IVRRenderModels_005 *_this, void * pD3D11Texture2D) { TRACE("%p\n", _this); - cppIVRRenderModels_IVRRenderModels_005_FreeTextureD3D11(_this->linux_side, pD3D11Texture2D); + ivrrendermodels_free_texture_d3d11(cppIVRRenderModels_IVRRenderModels_005_FreeTextureD3D11, _this->linux_side, pD3D11Texture2D, 5); } DEFINE_THISCALL_WRAPPER(winIVRRenderModels_IVRRenderModels_005_GetRenderModelName, 16) @@ -504,14 +504,14 @@ DEFINE_THISCALL_WRAPPER(winIVRRenderModels_IVRRenderModels_004_LoadTextureD3D11_ EVRRenderModelError __thiscall winIVRRenderModels_IVRRenderModels_004_LoadTextureD3D11_Async(winIVRRenderModels_IVRRenderModels_004 *_this, TextureID_t textureId, void * pD3D11Device, void ** ppD3D11Texture2D) { TRACE("%p\n", _this); - return cppIVRRenderModels_IVRRenderModels_004_LoadTextureD3D11_Async(_this->linux_side, textureId, pD3D11Device, ppD3D11Texture2D); + return ivrrendermodels_load_texture_d3d11_async(cppIVRRenderModels_IVRRenderModels_004_LoadTextureD3D11_Async, _this->linux_side, textureId, pD3D11Device, ppD3D11Texture2D, 4); } DEFINE_THISCALL_WRAPPER(winIVRRenderModels_IVRRenderModels_004_FreeTextureD3D11, 8) void __thiscall winIVRRenderModels_IVRRenderModels_004_FreeTextureD3D11(winIVRRenderModels_IVRRenderModels_004 *_this, void * pD3D11Texture2D) { TRACE("%p\n", _this); - cppIVRRenderModels_IVRRenderModels_004_FreeTextureD3D11(_this->linux_side, pD3D11Texture2D); + ivrrendermodels_free_texture_d3d11(cppIVRRenderModels_IVRRenderModels_004_FreeTextureD3D11, _this->linux_side, pD3D11Texture2D, 4); } DEFINE_THISCALL_WRAPPER(winIVRRenderModels_IVRRenderModels_004_GetRenderModelName, 16)