Signed-off-by: Jeff Smith whydoubt@gmail.com --- dlls/d3drm/d3drm.c | 44 +++++++++++--------------------- dlls/d3drm/tests/d3drm.c | 65 ++++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 80 insertions(+), 29 deletions(-)
diff --git a/dlls/d3drm/d3drm.c b/dlls/d3drm/d3drm.c index d0f20235a8..cba89e40cc 100644 --- a/dlls/d3drm/d3drm.c +++ b/dlls/d3drm/d3drm.c @@ -416,17 +416,13 @@ static HRESULT WINAPI d3drm1_CreateMaterial(IDirect3DRM *iface, static HRESULT WINAPI d3drm1_CreateDevice(IDirect3DRM *iface, DWORD width, DWORD height, IDirect3DRMDevice **device) { - struct d3drm_device *object; - HRESULT hr; - - FIXME("iface %p, width %u, height %u, device %p partial stub!\n", iface, width, height, device); + TRACE("iface %p, width %u, height %u, device %p.\n", iface, width, height, device);
- if (FAILED(hr = d3drm_device_create(&object, iface))) - return hr; - - *device = &object->IDirect3DRMDevice_iface; + if (!device) + return D3DRMERR_BADVALUE; + *device = NULL;
- return D3DRM_OK; + return D3DRMERR_BADDEVICE; }
static HRESULT WINAPI d3drm1_CreateDeviceFromSurface(IDirect3DRM *iface, GUID *guid, @@ -972,18 +968,13 @@ static HRESULT WINAPI d3drm2_CreateMaterial(IDirect3DRM2 *iface, static HRESULT WINAPI d3drm2_CreateDevice(IDirect3DRM2 *iface, DWORD width, DWORD height, IDirect3DRMDevice2 **device) { - struct d3drm *d3drm = impl_from_IDirect3DRM2(iface); - struct d3drm_device *object; - HRESULT hr; - - FIXME("iface %p, width %u, height %u, device %p partial stub!\n", iface, width, height, device); - - if (FAILED(hr = d3drm_device_create(&object, &d3drm->IDirect3DRM_iface))) - return hr; + TRACE("iface %p, width %u, height %u, device %p.\n", iface, width, height, device);
- *device = &object->IDirect3DRMDevice2_iface; + if (!device) + return D3DRMERR_BADVALUE; + *device = NULL;
- return D3DRM_OK; + return D3DRMERR_BADDEVICE; }
static HRESULT WINAPI d3drm2_CreateDeviceFromSurface(IDirect3DRM2 *iface, GUID *guid, @@ -1611,18 +1602,13 @@ static HRESULT WINAPI d3drm3_CreateMaterial(IDirect3DRM3 *iface, static HRESULT WINAPI d3drm3_CreateDevice(IDirect3DRM3 *iface, DWORD width, DWORD height, IDirect3DRMDevice3 **device) { - struct d3drm *d3drm = impl_from_IDirect3DRM3(iface); - struct d3drm_device *object; - HRESULT hr; - - FIXME("iface %p, width %u, height %u, device %p partial stub!\n", iface, width, height, device); + TRACE("iface %p, width %u, height %u, device %p.\n", iface, width, height, device);
- if (FAILED(hr = d3drm_device_create(&object, &d3drm->IDirect3DRM_iface))) - return hr; - - *device = &object->IDirect3DRMDevice3_iface; + if (!device) + return D3DRMERR_BADVALUE; + *device = NULL;
- return D3DRM_OK; + return D3DRMERR_BADDEVICE; }
static HRESULT WINAPI d3drm3_CreateDeviceFromSurface(IDirect3DRM3 *iface, GUID *guid, diff --git a/dlls/d3drm/tests/d3drm.c b/dlls/d3drm/tests/d3drm.c index 2fb2699f36..cc4f8fe16a 100644 --- a/dlls/d3drm/tests/d3drm.c +++ b/dlls/d3drm/tests/d3drm.c @@ -5370,6 +5370,68 @@ static void test_create_device_from_d3d3(void) DestroyWindow(window); }
+static void test_create_device_1(void) +{ + IDirect3DRM *d3drm = NULL; + IDirect3DRMDevice *device = (IDirect3DRMDevice *)0xdeadbeef; + HRESULT hr; + + hr = Direct3DRMCreate(&d3drm); + ok(hr == D3DRM_OK, "Cannot get IDirect3DRM interface (hr = %x).\n", hr); + + hr = IDirect3DRM_CreateDevice(d3drm, 640, 480, &device); + ok(hr == D3DRMERR_BADDEVICE, "Expected hr == D3DRMERR_BADDEVICE, got %x.\n", hr); + ok(device == NULL, "Expected device returned == NULL, got %p.\n", device); + hr = IDirect3DRM_CreateDevice(d3drm, 640, 480, NULL); + ok(hr == D3DRMERR_BADVALUE, "Expected hr == D3DRMERR_BADVALUE, got %x.\n", hr); + + IDirect3DRM_Release(d3drm); +} + +static void test_create_device_2(void) +{ + IDirect3DRM *d3drm = NULL; + IDirect3DRM2 *d3drm2 = NULL; + IDirect3DRMDevice2 *device2 = (IDirect3DRMDevice2 *)0xdeadbeef; + HRESULT hr; + + hr = Direct3DRMCreate(&d3drm); + ok(hr == D3DRM_OK, "Cannot get IDirect3DRM interface (hr = %x).\n", hr); + hr = IDirect3DRM_QueryInterface(d3drm, &IID_IDirect3DRM2, (void **)&d3drm2); + ok(hr == D3DRM_OK, "Cannot get IDirect3DRM3 interface (hr = %x).\n", hr); + + hr = IDirect3DRM2_CreateDevice(d3drm2, 640, 480, &device2); + ok(hr == D3DRMERR_BADDEVICE, "Expected hr == D3DRMERR_BADDEVICE, got %x.\n", hr); + ok(device2 == NULL, "Expected device returned == NULL, got %p.\n", device2); + hr = IDirect3DRM2_CreateDevice(d3drm2, 640, 480, NULL); + ok(hr == D3DRMERR_BADVALUE, "Expected hr == D3DRMERR_BADVALUE, got %x.\n", hr); + + IDirect3DRM2_Release(d3drm2); + IDirect3DRM_Release(d3drm); +} + +static void test_create_device_3(void) +{ + IDirect3DRM *d3drm = NULL; + IDirect3DRM3 *d3drm3 = NULL; + IDirect3DRMDevice3 *device3 = (IDirect3DRMDevice3 *)0xdeadbeef; + HRESULT hr; + + hr = Direct3DRMCreate(&d3drm); + ok(hr == D3DRM_OK, "Cannot get IDirect3DRM interface (hr = %x).\n", hr); + hr = IDirect3DRM_QueryInterface(d3drm, &IID_IDirect3DRM3, (void **)&d3drm3); + ok(hr == D3DRM_OK, "Cannot get IDirect3DRM3 interface (hr = %x).\n", hr); + + hr = IDirect3DRM3_CreateDevice(d3drm3, 640, 480, &device3); + ok(hr == D3DRMERR_BADDEVICE, "Expected hr == D3DRMERR_BADDEVICE, got %x.\n", hr); + ok(device3 == NULL, "Expected device returned == NULL, got %p.\n", device3); + hr = IDirect3DRM3_CreateDevice(d3drm3, 640, 480, NULL); + ok(hr == D3DRMERR_BADVALUE, "Expected hr == D3DRMERR_BADVALUE, got %x.\n", hr); + + IDirect3DRM3_Release(d3drm3); + IDirect3DRM_Release(d3drm); +} + static char *create_bitmap(unsigned int w, unsigned int h, BOOL palettized) { unsigned int bpp = palettized ? 8 : 24; @@ -7432,6 +7494,9 @@ START_TEST(d3drm) test_create_device_from_d3d1(); test_create_device_from_d3d2(); test_create_device_from_d3d3(); + test_create_device_1(); + test_create_device_2(); + test_create_device_3(); test_load_texture(); test_texture_qi(); test_viewport_qi();
There's no configuration in which the function succeeds? This would be surprising.
Regards, Fabian Maurer
I found it very odd myself, but I could not find a way to make it do anything else, and the only documentation I found on the method just says "Not implemented on the Windows platform."
On Fri, May 24, 2019 at 12:36 PM Fabian Maurer dark.shadow4@web.de wrote:
There's no configuration in which the function succeeds? This would be surprising.
Regards, Fabian Maurer
Am 24.05.19 um 20:28 schrieb Jeff Smith:
I found it very odd myself, but I could not find a way to make it do anything else, and the only documentation I found on the method just says "Not implemented on the Windows platform."
If I remember right when mentoring Aaryaman's GSoC project it only succeeded for an RGB device or something along those lines. It is quite possible though that CreateDevice fails while other ways (like CreateDeviceFromSurface, CreateDeviceFromD3D etc) succeed. This could be caused by d3drm trying to create a surface that's not supported on "modern" ddraw drivers for some reason.
The interesting platform to test d3drm stuff would be Windows 9.x, and maybe Windows 2000/XP. The DLL got removed from Vista, and only ancient games use it.
On Sun, May 26, 2019 at 10:13 PM Stefan Dösinger stefandoesinger@gmail.com wrote:
Am 24.05.19 um 20:28 schrieb Jeff Smith:
I found it very odd myself, but I could not find a way to make it do anything else, and the only documentation I found on the method just says "Not implemented on the Windows platform."
If I remember right when mentoring Aaryaman's GSoC project it only succeeded for an RGB device or something along those lines. It is quite possible though that CreateDevice fails while other ways (like CreateDeviceFromSurface, CreateDeviceFromD3D etc) succeed. This could be caused by d3drm trying to create a surface that's not supported on "modern" ddraw drivers for some reason.
The interesting platform to test d3drm stuff would be Windows 9.x, and maybe Windows 2000/XP. The DLL got removed from Vista, and only ancient games use it.
The interesting thing is that the tests are passing in 2000/XP as well.
I don't specifically remember why we skipped implementing CreateDevice earlier. I'll reply here if I do get more details about that.
By the way, which bug is CreateDevice related to?
On Sun, May 26, 2019, 9:26 AM Aaryaman Vasishta jem456.vasishta@gmail.com wrote:
On Sun, May 26, 2019 at 10:13 PM Stefan Dösinger < stefandoesinger@gmail.com> wrote:
Am 24.05.19 um 20:28 schrieb Jeff Smith:
I found it very odd myself, but I could not find a way to make it do anything else, and the only documentation I found on the method just says "Not implemented on the Windows platform."
If I remember right when mentoring Aaryaman's GSoC project it only succeeded for an RGB device or something along those lines. It is quite possible though that CreateDevice fails while other ways (like CreateDeviceFromSurface, CreateDeviceFromD3D etc) succeed. This could be caused by d3drm trying to create a surface that's not supported on "modern" ddraw drivers for some reason.
The interesting platform to test d3drm stuff would be Windows 9.x, and maybe Windows 2000/XP. The DLL got removed from Vista, and only ancient games use it.
The interesting thing is that the tests are passing in 2000/XP as well.
I don't specifically remember why we skipped implementing CreateDevice earlier. I'll reply here if I do get more details about that.
By the way, which bug is CreateDevice related to?
I just ran across this when developing test code for other parts of d3drm that I am looking to implement.
On Mon, May 27, 2019 at 12:43 AM Jeff Smith whydoubt@gmail.com wrote:
On Sun, May 26, 2019, 9:26 AM Aaryaman Vasishta jem456.vasishta@gmail.com wrote:
On Sun, May 26, 2019 at 10:13 PM Stefan Dösinger < stefandoesinger@gmail.com> wrote:
Am 24.05.19 um 20:28 schrieb Jeff Smith:
I found it very odd myself, but I could not find a way to make it do anything else, and the only documentation I found on the method just says "Not implemented on the Windows platform."
If I remember right when mentoring Aaryaman's GSoC project it only succeeded for an RGB device or something along those lines. It is quite possible though that CreateDevice fails while other ways (like CreateDeviceFromSurface, CreateDeviceFromD3D etc) succeed. This could be caused by d3drm trying to create a surface that's not supported on "modern" ddraw drivers for some reason.
The interesting platform to test d3drm stuff would be Windows 9.x, and maybe Windows 2000/XP. The DLL got removed from Vista, and only ancient games use it.
The interesting thing is that the tests are passing in 2000/XP as well.
I don't specifically remember why we skipped implementing CreateDevice earlier. I'll reply here if I do get more details about that.
By the way, which bug is CreateDevice related to?
I just ran across this when developing test code for other parts of d3drm that I am looking to implement.
I see. That's good to hear :) I'm glad to see more patches coming in for d3drm ^^
It would be interesting to have a test which checks how CreateDevice reacts when you pass a &device which was already created elsewhere (e.g., by CreateDeviceFromSurface/Clipper).
FWIW, I don't recall exactly how CreateDevice worked, but one way to find out its success case is by looking at d3drm documentation which is included in DX1-7 SDK. I currently lost my copy, but it seems like somebody had uploaded it in archive.org, so it may be worth checking. I'll probably take a look at it by next week, as this week is quite busy for me. Another way is to run wine with TRACE on games that use d3drm. A useful trick is to search for bugs related to d3drm and see if any of the applications mentioned in the bug uses this method.
Cheers, Aaryaman
On Sun, May 26, 2019 at 11:32 PM Aaryaman Vasishta jem456.vasishta@gmail.com wrote:
FWIW, I don't recall exactly how CreateDevice worked, but one way to find out its success case is by looking at d3drm documentation which is included in DX1-7 SDK.
When I mentioned earlier in the thread that the only documentation I could find stated "Not implemented on the Windows platform." that was from the SDK (DX6 and/or DX7). Also, I could not find any sample code using it.
Thanks, Jeff
On Sun, May 26, 2019 at 11:32 PM Aaryaman Vasishta jem456.vasishta@gmail.com wrote:
It would be interesting to have a test which checks how CreateDevice reacts when you pass a &device which was already created elsewhere (e.g., by CreateDeviceFromSurface/Clipper).
Not sure I would write a test for the suite, but from a few simple tests I did on Windows, it seems that all CreateDevice* methods ignore and replace the device that is passed in.
FWIW, I don't recall exactly how CreateDevice worked, but one way to find out its success case is by looking at d3drm documentation which is included in DX1-7 SDK. I currently lost my copy, but it seems like somebody had uploaded it in archive.org, so it may be worth checking. I'll probably take a look at it by next week, as this week is quite busy for me.
As I've said, DX6 and DX7 SDK docs simply state "Not implemented on the Windows platform." They do not even document the parameters beyond the prototype.
Another way is to run wine with TRACE on games that use d3drm. A useful trick is to search for bugs related to d3drm and see if any of the applications mentioned in the bug uses this method.
So far I have found neither a game that tries to call CreateDevice, nor a bug report that contains a use of it.
Thanks, Jeff
For what it's worth, it's not entirely unheard of for early versions of DirectDraw to have exports/interfaces that are simply unimplemented. It also looks that when these were originally implemented in 2012 (commit f018a861377edb96fecc7df644e04b0e9499897e), the main purpose was to introduce the various IDirect3DRMDevice stubs, and not so much CreateDevice() itself.