Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Setting a native DLL override for d3d9 is incorrect #150

Open
9ary opened this issue Mar 11, 2023 · 6 comments
Open

Setting a native DLL override for d3d9 is incorrect #150

9ary opened this issue Mar 11, 2023 · 6 comments

Comments

@9ary
Copy link
Contributor

9ary commented Mar 11, 2023

d3d9-nine.dll is a fake DLL, so setting a DLL override to native is incorrect. Installing it as d3d9.dll is sufficient, nine still works with the override removed.

To clarify: setting a DLL override to native means that wine should only load real DLLs, setting it to builtin means it should only load fake DLLs.

@dhewg
Copy link
Collaborator

dhewg commented Mar 14, 2023

It's only a fake DLL if installed in a certain way. Usually it is a unix library without the corresponding fake DLL.

The override is required on some WINE versions at least. When did that change?
We cannot rip out code if that breaks using nine on older WINE versions.

@9ary
Copy link
Contributor Author

9ary commented Mar 14, 2023

I doubt Wine has ever considered the .dll.so to be a native DLL, and it definitely doesn't think the fake DLL is one. Since 5.7 is apparently the oldest supported version, it'd be good to check what happens there.

@dhewg
Copy link
Collaborator

dhewg commented Mar 14, 2023

"native override" doesn't necessarily mean there's a win32 native DLL.

The override is required so WINE picks up a d3d9.dll copy from a prefix at all. Without it it would always use the wined3d copy from the WINE installation.

But since your arch package does the nine<->wine integration that picture changes and the override apparently gets useless and redundant.
AFAICT the override is still required without that integration, i.e. when using our binary releases with either nine-install.sh or winetricks.

@9ary
Copy link
Contributor Author

9ary commented Mar 14, 2023

I've packaged this project for NixOS as well (see #153), and I do not use the fake DLLs at all there. Nothing is installed to Wine's system path. Wine picks up d3d9.dll just fine with no override set at all.

I just did an experiment and the results are interesting. This is on Arch, Wine 8.3, nine 0.8. I've installed the (proper) d3d9.dll from nine into the Fusion 360 directory. AdCefWebBrowser.exe is in a subdirectory, so it never sees this DLL (I want it to use wined3d, due to rendering issues with nine).

  • no override: everything works, fusion uses nine
  • override for d3d9 set to builtin: ditto
  • override for d3d9 set to native: Fusion360.exe loads nine (I can see the message in the terminal), AdCefWebBrowser.exe fails to find d3d9.dll and crashes, which causes Fusion360.exe to crap out.
  • override set to disable: fusion won't start because it can't find d3d9

So it seems that Wine will load nine regardless of the override setting unless it's disabled. This sounds like a wine bug, unix libraries should be treated as builtin DLLs.

Messing with overrides for d3d9-nine.dll (with the fake dll installed to the prefix's system32):

  • no override: ninewinecfg loads nine successfully
  • builtin: same
  • native: ninewinecfg fails to load nine

This is the correct behavior.

@dhewg
Copy link
Collaborator

dhewg commented Mar 14, 2023

I'd have to test it again to make sure, but that sounds like a change in WINE behaviour to me.
Older WINE versions definitely need that override

@9ary
Copy link
Contributor Author

9ary commented Mar 17, 2023

I've managed to work around this by creating a DLL with no code, but all symbols forwarded to d3d9-nine. This DLL is recognized by wine as a native DLL, so I can drop it in system32, set a global override to builtin, and then an application-specific override for Fusion360.exe to native. The result is as expected: Fusion uses nine, and nothing else.

The downside is that I had to use mingw for this, it would be nice to figure out how to do this using winegcc instead, to avoid adding an extra build dependency.

d3d9.def (can be generated from the .spec with winebuild and then running a simple sed on the output):

LIBRARY d3d9.dll

EXPORTS
  Direct3DShaderValidatorCreate9=d3d9-nine.Direct3DShaderValidatorCreate9 @1
  PSGPError=d3d9-nine.PSGPError @2 PRIVATE
  PSGPSampleTexture=d3d9-nine.PSGPSampleTexture @3 PRIVATE
  D3DPERF_BeginEvent=d3d9-nine.D3DPERF_BeginEvent @4
  D3DPERF_EndEvent=d3d9-nine.D3DPERF_EndEvent @5
  D3DPERF_GetStatus=d3d9-nine.D3DPERF_GetStatus @6
  D3DPERF_QueryRepeatFrame=d3d9-nine.D3DPERF_QueryRepeatFrame @7
  D3DPERF_SetMarker=d3d9-nine.D3DPERF_SetMarker @8
  D3DPERF_SetOptions=d3d9-nine.D3DPERF_SetOptions @9
  D3DPERF_SetRegion=d3d9-nine.D3DPERF_SetRegion @10
  DebugSetLevel=d3d9-nine.DebugSetLevel @11 PRIVATE
  DebugSetMute=d3d9-nine.DebugSetMute @12
  Direct3DCreate9=d3d9-nine.Direct3DCreate9 @13
  Direct3DCreate9Ex=d3d9-nine.Direct3DCreate9Ex @14

Compile with x86_64-w64-mingw32-gcc d3d9.def -shared -o d3d9.dll.

Here's what happens if I try to use winegcc:

$ winegcc d3d9.def -shared -o d3d9.dll  -m64 -mwindows -L/nonexistant 
tmp64180562/d3d9-00000000.spec-00000000.s: Assembler messages:
tmp64180562/d3d9-00000000.spec-00000000.s:2: Error: can't resolve d3d9 - nine.Direct3DShaderValidatorCreate9
tmp64180562/d3d9-00000000.spec-00000000.s:3: Error: can't resolve d3d9 - nine.PSGPError
tmp64180562/d3d9-00000000.spec-00000000.s:4: Error: can't resolve d3d9 - nine.PSGPSampleTexture
tmp64180562/d3d9-00000000.spec-00000000.s:5: Error: can't resolve d3d9 - nine.D3DPERF_BeginEvent
tmp64180562/d3d9-00000000.spec-00000000.s:6: Error: can't resolve d3d9 - nine.D3DPERF_EndEvent
tmp64180562/d3d9-00000000.spec-00000000.s:7: Error: can't resolve d3d9 - nine.D3DPERF_GetStatus
tmp64180562/d3d9-00000000.spec-00000000.s:8: Error: can't resolve d3d9 - nine.D3DPERF_QueryRepeatFrame
tmp64180562/d3d9-00000000.spec-00000000.s:9: Error: can't resolve d3d9 - nine.D3DPERF_SetMarker
tmp64180562/d3d9-00000000.spec-00000000.s:10: Error: can't resolve d3d9 - nine.D3DPERF_SetOptions
tmp64180562/d3d9-00000000.spec-00000000.s:11: Error: can't resolve d3d9 - nine.D3DPERF_SetRegion
tmp64180562/d3d9-00000000.spec-00000000.s:12: Error: can't resolve d3d9 - nine.DebugSetLevel
tmp64180562/d3d9-00000000.spec-00000000.s:13: Error: can't resolve d3d9 - nine.DebugSetMute
tmp64180562/d3d9-00000000.spec-00000000.s:14: Error: can't resolve d3d9 - nine.Direct3DCreate9
tmp64180562/d3d9-00000000.spec-00000000.s:15: Error: can't resolve d3d9 - nine.Direct3DCreate9Ex
winebuild: /usr/bin/gcc failed with status 1
winegcc: /usr/bin/winebuild failed

Edit: I managed to make a DLL using winebuild, but for some reason it causes Fusion to be unresponsive for a while at startup before it becomes usable. This isn't a problem with the mingw DLL...

@9ary 9ary mentioned this issue Mar 18, 2023
9ary added a commit to 9ary/wine-nine-standalone that referenced this issue Mar 18, 2023
Because Wine appears to ignore override settings for .dll.so libraries,
introduce a forwarding DLL that will always be identified as native.

Fixes iXit#150
9ary added a commit to 9ary/wine-nine-standalone that referenced this issue Mar 18, 2023
Because Wine appears to ignore override settings for .dll.so libraries,
introduce a forwarding DLL that will always be identified as native.

Fixes iXit#150
9ary added a commit to 9ary/wine-nine-standalone that referenced this issue Mar 19, 2023
Because Wine appears to ignore override settings for .dll.so libraries,
introduce a forwarding DLL that will always be identified as native.

Fixes iXit#150
9ary added a commit to 9ary/wine-nine-standalone that referenced this issue Mar 19, 2023
Because Wine appears to ignore override settings for .dll.so libraries,
introduce a forwarding DLL that will always be identified as native.

Fixes iXit#150
9ary added a commit to 9ary/wine-nine-standalone that referenced this issue Apr 12, 2023
Because Wine appears to ignore override settings for .dll.so libraries,
introduce a forwarding DLL that will always be identified as native.

Fixes iXit#150
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants