-
-
Notifications
You must be signed in to change notification settings - Fork 440
Description
Summary
For certain overload of the Assimp.GetMaterialString, there is a code that copies managed string to global memory and passes the pointer to native method. However when it returns, it attempts to convert to string (SilkMarshal.PtrToString) which is useless since the resulting string is not use anywhere.
The aforementioned PtrToString (or rather Utf8PtrToString used for the used LPUTF8Str encoding) then can cause AccessViolationException because the way it is implemented is it scans for null-terminator in Span<byte>(ptr, int.MaxValue) which can use vectorization instructions and "look ahead". However when the pointer is near the edge of accessible memory, this can fail.
So technically there are two issues: unnecessary pointer to string conversion, and Access Violation risk when using Utf8PtrToString
Steps to reproduce
- Platform: Desktop
- Framework Version: .NET 8
- Tested Nuget Versions: 2.13.0, 2.20.0
I wasn't able to create easy repro, but the bug was encountered after using Silk.NET.Assimp like this:
string GetMaterialName(Material* material)
{
AssimpString materialName = new AssimpString();
_assimp.GetMaterialString(material, Assimp.MaterialNameBase, 0, 0, ref materialName);
...Fatal error. System.AccessViolationException: Attempted to read or write protected memory. This is often an indication that other memory is corrupt.
at System.SpanHelpers.NonPackedIndexOfValueType[[System.Byte, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e],[System.SpanHelpers+DontNegate`1[[System.Byte, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e]], System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e]](Byte ByRef, Byte, Int32)
at System.MemoryExtensions.IndexOf[[System.Byte, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e]](System.Span`1<Byte>, Byte)
at Silk.NET.Core.Native.SilkMarshal.Utf8PtrToString(IntPtr)
at Silk.NET.Core.Native.SilkMarshal.PtrToString(IntPtr, Silk.NET.Core.Native.NativeStringEncoding)
at Silk.NET.Assimp.Assimp.GetMaterialString(Silk.NET.Assimp.Material*, System.String, UInt32, UInt32, Silk.NET.Assimp.AssimpString ByRef)
Comments
In the following image, the highlighted code shouldn't be necessary at all.

Metadata
Metadata
Assignees
Labels
Type
Projects
Status