From 1ce0efdd605511a411c3d577de3ca2632af9ffec Mon Sep 17 00:00:00 2001 From: Sebastian Lackner Date: Tue, 28 Jul 2015 17:37:05 +0200 Subject: [PATCH] Added patch to return dummy ID3DXSkinInfo interface when skinning info not present. --- README.md | 3 +- debian/changelog | 2 + ...dummy-skininfo-interface-in-D3DXLoad.patch | 81 +++++++++ ...dd-initial-tests-for-dummy-skininfo-.patch | 164 ++++++++++++++++++ patches/d3dx9_36-Dummy_Skininfo/definition | 1 + patches/patchinstall.sh | 21 +++ 6 files changed, 271 insertions(+), 1 deletion(-) create mode 100644 patches/d3dx9_36-Dummy_Skininfo/0001-d3dx9_36-Return-dummy-skininfo-interface-in-D3DXLoad.patch create mode 100644 patches/d3dx9_36-Dummy_Skininfo/0002-d3dx9_36-tests-Add-initial-tests-for-dummy-skininfo-.patch create mode 100644 patches/d3dx9_36-Dummy_Skininfo/definition diff --git a/README.md b/README.md index f32f44e8..e1716963 100644 --- a/README.md +++ b/README.md @@ -39,7 +39,7 @@ Wine. All those differences are also documented on the Included bug fixes and improvements ----------------------------------- -**Bug fixes and features included in the next upcoming release [10]:** +**Bug fixes and features included in the next upcoming release [11]:** * Add stubs for d3dx10_43.D3DX10CreateEffectFromFileA/W ([Wine Bug #27739](https://bugs.winehq.org/show_bug.cgi?id=27739)) * Add support for ThreadQuerySetWin32StartAddress info class ([Wine Bug #8277](https://bugs.winehq.org/show_bug.cgi?id=8277)) @@ -49,6 +49,7 @@ Included bug fixes and improvements * Fix loading of libraries with incomplete IMAGE_LOAD_CONFIG_DIRECTORY struct * Fix security cookie handling for UPX compressed executables ([Wine Bug #38949](https://bugs.winehq.org/show_bug.cgi?id=38949)) * Forward exitcode from child process when in wineconsole +* Return dummy ID3DXSkinInfo interface when skinning info not present ([Wine Bug #33904](https://bugs.winehq.org/show_bug.cgi?id=33904)) * Share source of d3dx9_36 with d3dx9_33 to avoid Wine DLL forwards ([Wine Bug #21817](https://bugs.winehq.org/show_bug.cgi?id=21817)) * Silence repeated LocaleNameToLCID/LCIDToLocaleName unsupported flags FIXMEs ([Wine Bug #30076](https://bugs.winehq.org/show_bug.cgi?id=30076)) diff --git a/debian/changelog b/debian/changelog index 2dabf595..5d00c13f 100644 --- a/debian/changelog +++ b/debian/changelog @@ -15,6 +15,8 @@ wine-staging (1.7.48) UNRELEASED; urgency=low * Added patches to implement ThreadQuerySetWin32StartAddress info class. * Added patch to fake success in kernel32.SetFileCompletionNotificationModes. * Added patch to export additional OpenAL32 functions. + * Added patch to return dummy ID3DXSkinInfo interface when skinning info not + present. * Removed patch to allow to enable/disable InsertMode in wineconsole settings (accepted upstream). * Removed patch to improve IoGetDeviceObjectPointer stub to appease SecuROM diff --git a/patches/d3dx9_36-Dummy_Skininfo/0001-d3dx9_36-Return-dummy-skininfo-interface-in-D3DXLoad.patch b/patches/d3dx9_36-Dummy_Skininfo/0001-d3dx9_36-Return-dummy-skininfo-interface-in-D3DXLoad.patch new file mode 100644 index 00000000..57088a9e --- /dev/null +++ b/patches/d3dx9_36-Dummy_Skininfo/0001-d3dx9_36-Return-dummy-skininfo-interface-in-D3DXLoad.patch @@ -0,0 +1,81 @@ +From 95b6016b7cfb62a70ec9bbcc39117f68259aa93b Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?Michael=20M=C3=BCller?= +Date: Tue, 28 Jul 2015 17:26:09 +0200 +Subject: d3dx9_36: Return dummy skininfo interface in D3DXLoadSkinMeshFromXof + when skin information is unavailable. + +--- + dlls/d3dx9_36/d3dx9_36_private.h | 2 ++ + dlls/d3dx9_36/mesh.c | 7 +++++++ + dlls/d3dx9_36/skin.c | 22 +++++++++++++++++++++- + 3 files changed, 30 insertions(+), 1 deletion(-) + +diff --git a/dlls/d3dx9_36/d3dx9_36_private.h b/dlls/d3dx9_36/d3dx9_36_private.h +index 79f3b76..b6707f6 100644 +--- a/dlls/d3dx9_36/d3dx9_36_private.h ++++ b/dlls/d3dx9_36/d3dx9_36_private.h +@@ -110,4 +110,6 @@ const char *debug_d3dxparameter_registerset(D3DXREGISTER_SET r) DECLSPEC_HIDDEN; + void set_number(void *outdata, D3DXPARAMETER_TYPE outtype, + const void *indata, D3DXPARAMETER_TYPE intype) DECLSPEC_HIDDEN; + ++HRESULT create_dummy_skin(ID3DXSkinInfo **iface) DECLSPEC_HIDDEN; ++ + #endif /* __WINE_D3DX9_36_PRIVATE_H */ +diff --git a/dlls/d3dx9_36/mesh.c b/dlls/d3dx9_36/mesh.c +index 4aeac26..3cd85a3 100644 +--- a/dlls/d3dx9_36/mesh.c ++++ b/dlls/d3dx9_36/mesh.c +@@ -3334,6 +3334,13 @@ static HRESULT parse_mesh(ID3DXFileData *filedata, struct mesh_data *mesh_data, + goto end; + } + ++ if ((provide_flags & PROVIDE_SKININFO) && !mesh_data->skin_info) ++ { ++ hr = create_dummy_skin(&mesh_data->skin_info); ++ if (FAILED(hr)) ++ goto end; ++ } ++ + hr = D3D_OK; + + end: +diff --git a/dlls/d3dx9_36/skin.c b/dlls/d3dx9_36/skin.c +index 9b93af6..3d68829 100644 +--- a/dlls/d3dx9_36/skin.c ++++ b/dlls/d3dx9_36/skin.c +@@ -92,7 +92,7 @@ static ULONG WINAPI d3dx9_skin_info_Release(ID3DXSkinInfo *iface) + HeapFree(GetProcessHeap(), 0, skin->bones[i].vertices); + HeapFree(GetProcessHeap(), 0, skin->bones[i].weights); + } +- HeapFree(GetProcessHeap(), 0, skin->bones); ++ if (skin->bones) HeapFree(GetProcessHeap(), 0, skin->bones); + HeapFree(GetProcessHeap(), 0, skin); + } + +@@ -493,3 +493,23 @@ HRESULT WINAPI D3DXCreateSkinInfoFVF(DWORD num_vertices, DWORD fvf, DWORD num_bo + + return D3DXCreateSkinInfo(num_vertices, declaration, num_bones, skin_info); + } ++ ++HRESULT create_dummy_skin(ID3DXSkinInfo **iface) ++{ ++ static const D3DVERTEXELEMENT9 empty_declaration = D3DDECL_END(); ++ struct d3dx9_skin_info *object = NULL; ++ ++ object = HeapAlloc(GetProcessHeap(), 0, sizeof(*object)); ++ if (!object) return E_OUTOFMEMORY; ++ ++ object->ID3DXSkinInfo_iface.lpVtbl = &d3dx9_skin_info_vtbl; ++ object->ref = 1; ++ object->num_vertices = 0; ++ object->num_bones = 0; ++ object->vertex_declaration[0] = empty_declaration; ++ object->fvf = 0; ++ object->bones = NULL; ++ ++ *iface = &object->ID3DXSkinInfo_iface; ++ return D3D_OK; ++} +-- +2.4.5 + diff --git a/patches/d3dx9_36-Dummy_Skininfo/0002-d3dx9_36-tests-Add-initial-tests-for-dummy-skininfo-.patch b/patches/d3dx9_36-Dummy_Skininfo/0002-d3dx9_36-tests-Add-initial-tests-for-dummy-skininfo-.patch new file mode 100644 index 00000000..dc3dd0af --- /dev/null +++ b/patches/d3dx9_36-Dummy_Skininfo/0002-d3dx9_36-tests-Add-initial-tests-for-dummy-skininfo-.patch @@ -0,0 +1,164 @@ +From f54e1b037a6d3ecb97623d930e71d14d1309ba2f Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?Michael=20M=C3=BCller?= +Date: Tue, 28 Jul 2015 17:34:40 +0200 +Subject: d3dx9_36/tests: Add initial tests for dummy skininfo interface. + +--- + dlls/d3dx9_36/tests/mesh.c | 127 +++++++++++++++++++++++++++++++++++++++++++++ + 1 file changed, 127 insertions(+) + +diff --git a/dlls/d3dx9_36/tests/mesh.c b/dlls/d3dx9_36/tests/mesh.c +index dac0f60..62e7113 100644 +--- a/dlls/d3dx9_36/tests/mesh.c ++++ b/dlls/d3dx9_36/tests/mesh.c +@@ -25,6 +25,9 @@ + #include + #include "wine/test.h" + #include "d3dx9.h" ++#include "initguid.h" ++#include "rmxftmpl.h" ++#include "rmxfguid.h" + + #ifndef NAN + /* From wine/port.h */ +@@ -2433,6 +2436,129 @@ cleanup: + if (wnd) DestroyWindow(wnd); + } + ++static ID3DXFileData *get_mesh_data(const char *memory, SIZE_T length) ++{ ++ D3DXF_FILELOADMEMORY source; ++ ID3DXFileEnumObject *enumobj = NULL; ++ ID3DXFileData *filedata = NULL; ++ ID3DXFileData *ret = NULL; ++ ID3DXFile *d3dxfile = NULL; ++ SIZE_T i, nb_children; ++ HRESULT hr; ++ GUID guid; ++ ++ hr = D3DXFileCreate(&d3dxfile); ++ if (FAILED(hr)) return NULL; ++ ++ hr = d3dxfile->lpVtbl->RegisterTemplates(d3dxfile, D3DRM_XTEMPLATES, D3DRM_XTEMPLATE_BYTES); ++ if (FAILED(hr)) goto cleanup; ++ ++ source.lpMemory = (void *)memory; ++ source.dSize = length; ++ ++ hr = d3dxfile->lpVtbl->CreateEnumObject(d3dxfile, &source, D3DXF_FILELOAD_FROMMEMORY, &enumobj); ++ if (FAILED(hr)) goto cleanup; ++ ++ hr = enumobj->lpVtbl->GetChildren(enumobj, &nb_children); ++ if (FAILED(hr)) goto cleanup; ++ ++ for (i = 0; i < nb_children; i++) ++ { ++ hr = enumobj->lpVtbl->GetChild(enumobj, i, &filedata); ++ if (FAILED(hr)) goto cleanup; ++ ++ hr = filedata->lpVtbl->GetType(filedata, &guid); ++ if (SUCCEEDED(hr) && IsEqualGUID(&guid, &TID_D3DRMMesh)) ++ { ++ ret = filedata; ++ break; ++ } ++ else ++ filedata->lpVtbl->Release(filedata); ++ } ++ ++cleanup: ++ if (enumobj) enumobj->lpVtbl->Release(enumobj); ++ if (d3dxfile) d3dxfile->lpVtbl->Release(d3dxfile); ++ ++ return ret; ++} ++ ++static void D3DXLoadSkinMeshFromXofTest(void) ++{ ++ static const char simple_xfile[] = ++ "xof 0303txt 0032" ++ "Mesh {" ++ "3;" ++ "0.0; 0.0; 0.0;," ++ "0.0; 1.0; 0.0;," ++ "1.0; 1.0; 0.0;;" ++ "1;" ++ "3; 0, 1, 2;;" ++ "}"; ++ ID3DXBuffer *adjacency, *materials, *effects; ++ D3DPRESENT_PARAMETERS d3dpp; ++ IDirect3DDevice9 *device; ++ ID3DXFileData *filedata; ++ ID3DXSkinInfo *skininfo; ++ ID3DXMesh *mesh; ++ IDirect3D9 *d3d; ++ DWORD mat_count; ++ HRESULT hr; ++ HWND hwnd; ++ ++ if (!(hwnd = CreateWindowA("static", "d3dx9_test", WS_OVERLAPPEDWINDOW, 0, 0, ++ 640, 480, NULL, NULL, NULL, NULL))) ++ { ++ skip("Couldn't create application window\n"); ++ return; ++ } ++ ++ d3d = Direct3DCreate9(D3D_SDK_VERSION); ++ if (!d3d) ++ { ++ skip("Couldn't create IDirect3D9 object\n"); ++ DestroyWindow(hwnd); ++ return; ++ } ++ ++ ZeroMemory(&d3dpp, sizeof(d3dpp)); ++ d3dpp.Windowed = TRUE; ++ d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD; ++ ++ hr = IDirect3D9_CreateDevice(d3d, D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, hwnd, D3DCREATE_SOFTWARE_VERTEXPROCESSING, &d3dpp, &device); ++ IDirect3D9_Release(d3d); ++ if (FAILED(hr)) ++ { ++ skip("Failed to create IDirect3DDevice9 object %#x\n", hr); ++ DestroyWindow(hwnd); ++ return; ++ } ++ ++ filedata = get_mesh_data(simple_xfile, sizeof(simple_xfile) - 1); ++ ok(filedata != NULL, "Failed to load mesh data\n"); ++ ++ adjacency = materials = effects = NULL; ++ skininfo = NULL; ++ mesh = NULL; ++ ++ hr = D3DXLoadSkinMeshFromXof(filedata, 0, device, &adjacency, &materials, &effects, &mat_count, &skininfo, &mesh); ++ ok(hr == D3D_OK, "Got result %x, expected 0 (D3D_OK)\n", hr); ++ ok(skininfo != NULL, "Expected non-null skininfo\n"); ++ ++ /* FIXME: Add additional tests for skininfo interface. */ ++ ++ if (adjacency) adjacency->lpVtbl->Release(adjacency); ++ if (materials) materials->lpVtbl->Release(materials); ++ if (effects) effects->lpVtbl->Release(effects); ++ if (skininfo) skininfo->lpVtbl->Release(skininfo); ++ if (mesh) mesh->lpVtbl->Release(mesh); ++ ++ filedata->lpVtbl->Release(filedata); ++ IDirect3DDevice9_Release(device); ++ DestroyWindow(hwnd); ++} ++ + static BOOL compute_box(struct mesh *mesh, float width, float height, float depth) + { + unsigned int i, face; +@@ -10613,6 +10739,7 @@ START_TEST(mesh) + D3DXCreateMeshTest(); + D3DXCreateMeshFVFTest(); + D3DXLoadMeshTest(); ++ D3DXLoadSkinMeshFromXofTest(); + D3DXCreateBoxTest(); + D3DXCreatePolygonTest(); + D3DXCreateSphereTest(); +-- +2.4.5 + diff --git a/patches/d3dx9_36-Dummy_Skininfo/definition b/patches/d3dx9_36-Dummy_Skininfo/definition new file mode 100644 index 00000000..f8f3d4c8 --- /dev/null +++ b/patches/d3dx9_36-Dummy_Skininfo/definition @@ -0,0 +1 @@ +Fixes: [33904] Return dummy ID3DXSkinInfo interface when skinning info not present diff --git a/patches/patchinstall.sh b/patches/patchinstall.sh index b948aff4..3fe37935 100755 --- a/patches/patchinstall.sh +++ b/patches/patchinstall.sh @@ -99,6 +99,7 @@ patch_enable_all () enable_d3dx9_36_DDS="$1" enable_d3dx9_36_DXTn="$1" enable_d3dx9_36_DrawText="$1" + enable_d3dx9_36_Dummy_Skininfo="$1" enable_d3dx9_36_Filter_Warnings="$1" enable_d3dx9_36_FindNextValidTechnique="$1" enable_d3dx9_36_GetShaderSemantics="$1" @@ -371,6 +372,9 @@ patch_enable () d3dx9_36-DrawText) enable_d3dx9_36_DrawText="$2" ;; + d3dx9_36-Dummy_Skininfo) + enable_d3dx9_36_Dummy_Skininfo="$2" + ;; d3dx9_36-Filter_Warnings) enable_d3dx9_36_Filter_Warnings="$2" ;; @@ -2363,6 +2367,23 @@ if test "$enable_d3dx9_36_DrawText" -eq 1; then ) >> "$patchlist" fi +# Patchset d3dx9_36-Dummy_Skininfo +# | +# | This patchset fixes the following Wine bugs: +# | * [#33904] Return dummy ID3DXSkinInfo interface when skinning info not present +# | +# | Modified files: +# | * dlls/d3dx9_36/d3dx9_36_private.h, dlls/d3dx9_36/mesh.c, dlls/d3dx9_36/skin.c, dlls/d3dx9_36/tests/mesh.c +# | +if test "$enable_d3dx9_36_Dummy_Skininfo" -eq 1; then + patch_apply d3dx9_36-Dummy_Skininfo/0001-d3dx9_36-Return-dummy-skininfo-interface-in-D3DXLoad.patch + patch_apply d3dx9_36-Dummy_Skininfo/0002-d3dx9_36-tests-Add-initial-tests-for-dummy-skininfo-.patch + ( + echo '+ { "Michael Müller", "d3dx9_36: Return dummy skininfo interface in D3DXLoadSkinMeshFromXof when skin information is unavailable.", 1 },'; + echo '+ { "Michael Müller", "d3dx9_36/tests: Add initial tests for dummy skininfo interface.", 1 },'; + ) >> "$patchlist" +fi + # Patchset d3dx9_36-Filter_Warnings # | # | This patchset fixes the following Wine bugs: