dotnet / wpf

WPF is a .NET Core UI framework for building Windows desktop applications.
MIT License
6.93k stars 1.15k forks source link

Consider using CsWin32 for win32 Interop code #7007

Open elachlan opened 1 year ago

elachlan commented 1 year ago

dotnet/winforms is currently working through a migration of the interop code to use CsWin32. The associated issue can be found at https://github.com/dotnet/winforms/issues/7445. CsWin32 makes use of the win32Metadata project. Improvements in the metadata and CsWin32 help improve all projects that make use of it and reduces the amount of interop code maintained in the project.

dotnet/wpf should consider making use of CsWin32 to gain access to these improvements and to help improve the ecosystem.

elachlan commented 1 year ago

@JeremyKuhne I have created a similar issue here in wpf, which if adopted wil be able to make use of the effort done in winforms.

oysteinkrog commented 1 year ago

Is this the same as using LibraryImport source generator? It seems like LibraryImport generator is the official story moving forward?

elachlan commented 1 year ago

@AArnott can explain it better than myself.

CsWin3w provides the pinvoke stubs and friendly overrides for the win32 API. As well as any structures, enums and constants. It only provides the API surface you request.

These underlying metadata is provided by win32metadata. Which is used by many different language projections.

This reduces the code for pinvokes significantly, since it's all generated by CsWin32.

AArnott commented 1 year ago

Is this the same as using LibraryImport source generator? It seems like LibraryImport generator is the official story moving forward?

LibraryImport is essentially just a newer DllImport that works in trimming scenarios where DllImport wouldn't. It emits enough code that the .NET marshaler never has to get involved, which can improve perf. But the heavy lifting of declaring the extern method signature and all the interop types (structs, enums, etc) is still all the developer's responsibility. CsWin32 generates all this for you just by your naming a single API (e.g. CreateFile).

CsWin32's generated code still uses DllImport (as does LibraryImport, under the covers). So the only remaining issue with using CsWin32 is that it isn't battle hardened for trimmed apps like LibraryImport is. But the LibraryImport folks are talking about exposing their source generator as a library so that other source generators including CsWin32 can consume it. I look forward to consuming this, which will give you all the benefits of LibraryImport's trim-friendly code and the super easy-to-use CsWin32 way of getting whatever API you want just by asking for it. :)

So that all said, I support the recommendation that you consider using CsWin32 for all your new win32 interop code, and consider migrating existing APIs you hand-wrote over to CsWin32. The future is bright. :)

elachlan commented 1 month ago

I am bumping here as there has been a massive amount of work done to get Winforms using CsWin32. WPF could make use of that to greatly reduce the conversion time.