Although I’m guessing from the Box2d name that you are working with structs that somehow use native code, making parts of it as the error say’s unaddressable.
Ah ok, that makes sense as the type has some funky things going on.
No native code. I’ve ported box2d to Unity DOTS.
The struct is the b2ClipVertex. Thanks for letting me know it’s to do with the type. I can probably work from that information.
ResizableArray64Byte<b2ClipVertex> clipPoints1 = new ResizableArray64Byte<b2ClipVertex> ();
public struct b2ClipVertex
{
public float2 v;
public b2ContactID id;
};
[StructLayout(LayoutKind.Explicit)]
public struct b2ContactID
{
[FieldOffset(0)]
public b2ContactFeature cf;
[FieldOffset(0)]
public uint key; ///< Used to quickly compare contact ids.
};
public struct b2ContactFeature
{
public const uint8 b2_nullFeature = uint8.MaxValue;
public enum Type
{
e_vertex = 0,
e_face = 1
};
public uint8 indexA; ///< Feature index on shapeA
public uint8 indexB; ///< Feature index on shapeB
public uint8 typeA; ///< The feature type on shapeA
public uint8 typeB; ///< The feature type on shapeB
};
You are specifying two types with different lengths at the same FieldOffset. Not surprised burst blew up on this. C# won’t blow up but I’m sure it’s not doing what you would expect, or what Box2D does.
int size1 = System.Runtime.InteropServices.Marshal.SizeOf (typeof(b2ContactFeature));
int size2 = System.Runtime.InteropServices.Marshal.SizeOf (typeof(uint));
Both are 4 bytes. Are you referring to something else when you say length other than size in bytes?
The equivalent in C++ Box2d:
union b2ContactID
{
b2ContactFeature cf;
uint32 key; ///< Used to quickly compare contact ids.
};
[StructLayout(LayoutKind.Explicit)]
struct TestLayoutStruct
{
[FieldOffset(0)]
public int a;
[FieldOffset(0)]
public int b;
}
struct TestLayoutStruct2
{
public TestLayoutStruct c;
}
[BurstCompile]
struct TestLayoutJob : IJob
{
public void Execute ()
{
NativeArray<TestLayoutStruct2> testArray = new NativeArray<TestLayoutStruct2> (2, Allocator.Temp);
testArray [0] = new TestLayoutStruct2 ();
testArray [1] = new TestLayoutStruct2 ();
var r1 = testArray [0].c.a;
var r2 = testArray [0].c.b;
}
}
error: Unexpected error while processing instruction `IL_003c: ldfld System.Int32 Sim.b2World/TestLayoutStruct::a args(IL_0037)`. Reason: The struct field Sim.b2World/TestLayoutStruct Sim.b2World/TestLayoutStruct2::c's struct comes from an unaddressable source: IL_0032: call !0 Unity.Collections.NativeArray`1<Sim.b2World/TestLayoutStruct2>::get_Item(System.Int32) args(IL_002f, IL_0031)
Ya you are right I was reading it wrong. I don’t know what all the rules are for FieldOffset I’ve only ever used it in the context of a single struct. But I took your last example and used explicit and FieldOffset on the second struct, and that works. So it seems burst only supports very explicit mapping scenarios maybe.