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

Comment on System.Numerics in the readme #1

Closed
kumpera opened this issue May 18, 2020 · 7 comments
Closed

Comment on System.Numerics in the readme #1

kumpera opened this issue May 18, 2020 · 7 comments

Comments

@kumpera
Copy link

kumpera commented May 18, 2020

From the readme:

If you wonder why I’m not using System.Numerics — structures from there lack [StructLayout( LayoutKind.Sequential )] which is absolute requirement for native interop. And given Microsoft’s stance on backward compatibility, not sure they ever fix it.

C# structs use sequential layout by default, which means they all are.

@tannergooding
Copy link

Was just going to comment the same 😄

C# emits classes using LayoutKind.Auto while it emits structs using LayoutKind.Sequential by default (the latter differs from the same type declared directly in IL) and while we (the .NET Libraries Team) don't necessarily guarantee any struct will always stay blittable or that it won't have the underlying layout changed, the Vector2/3/4, Matrix3x2, Matrix4x4, Plane, and Quaternion types in particular won't change as they publicly expose their fields and have explicit size/layout requirements.

@Const-me
Copy link
Owner

Const-me commented May 18, 2020

Thanks for the tip. Will leave this issue open and upgrade when I’ll have time.

Will definitely work for vectors, quaternions and 4x4 matrices

About 3x2 matrices, do you happen to know have someone tested Matrix3x2 from .NET against the corresponding C++ class from Windows SDK? https://docs.microsoft.com/en-us/windows/win32/api/d2d1helper/nl-d2d1helper-matrix3x2f

I did and I think I had to make some compatibility adjustments to my initial implementation of these matrices.

@tannergooding
Copy link

Matrix3x2F is not a C++03 POD ("Plain Old Data") type and so it may have different marshaling characteristics/requirements. We should be largely compatible with D2D_MATRIX_3X2_F but that will likely depend on the underlying ABI (Application Binary Interface), that is the Calling Convention used, as D2D_MATRIX_3X2_F is a struct containing a union of two structs (each having 6x float fields) and a byval array that is 3x2 in width while System.Numerics.Matrix3x2 is simply a struct containing 6x float fields

@Const-me
Copy link
Owner

An example of the upper layer of the ABI: https://github.com/Const-me/Vrmac/blob/master/VrmacInterop/Draw/Direct2D/iDrawContext.cs#L29 There’re more methods passing them between C++ and C#, they are used a lot over both 2D backends.

When running on Windows, my COM runtime compiles that method into unmanaged delegate with CallingConvention.StdCall applied: https://github.com/Const-me/ComLightInterop/blob/master/ComLight/Emit/NativeDelegates.cs#L43-L48

On Windows, the layer below that are C++ methods with __stdcall convention, built by Visual Studio 2017 for AMD64. I have no intentions to change that any time soon, in my experience platform-default compilers cause least amount of issues, on Windows this means MSVC, on Linux GCC.

Does this mean the 3x2 matrices from .NET Numerics are binary compatible with D2D matrices?

Also, do you happen to know the operations on these matrices, especially vector transform and inversion, are identical (apart from inevitable float precision issues caused by FMA and other factors, I’m fine with them) across the 2 implementations, in .NET and D2D?

@tannergooding
Copy link

Does this mean the 3x2 matrices from .NET Numerics are binary compatible with D2D matrices?

It would depend on the underlying ABI and would require more investigation. I believe in the case of Matrix3x2 they are compatible, but there can be lots of tiny nuances when you actually dig into things: https://docs.microsoft.com/en-us/cpp/build/x64-calling-convention?view=vs-2019#return-values

Also, do you happen to know the operations on these matrices, especially vector transform and inversion, are identical (apart from inevitable float precision issues caused by FMA and other factors, I’m fine with them) across the 2 implementations, in .NET and D2D?

I haven't done any analysis to determine if we are or are not compatible with the Direct2D algorithms (or DirectX Math). In general, I would expect results to at least be similar.

@Const-me
Copy link
Owner

@tannergooding Fixed now. Will release 1.1 after improving couple more things.

Had no compatibility issues with 3x2 matrices, tested both 2D backends on Windows, and my custom one on Linux.

But I had a couple with 4x4 ones: https://github.com/Const-me/Vrmac/blob/master/Vrmac/Utils/Math/DiligentMatrices.cs The projection was expected, but I forgot I have also patched LookAt in the old MonoGame-based code.

@Const-me
Copy link
Owner

Fixed in 1.1

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

3 participants