C# System.TypeLoadException : Could not load type because it contains an object field at offset - code from . .net 核心上的 net 框架

标签 c# .net .net-core

我正在尝试使用 ets2sdk .net 核心项目中的库(最初是用 .net 框架编写的)。

加载此类型导致异常:

System.TypeLoadException: Could not load type 'Ets2SdkData' from assembly 'x' because it contains an object field at offset 20 that is incorrectly aligned or overlapped by a non-object field.

类型正文:

[StructLayout(LayoutKind.Explicit)]
public struct Ets2SdkData
{
    [FieldOffset(0)]
    public uint time;
    [FieldOffset(4)]
    public uint paused;

    [FieldOffset(8)]
    public uint ets2_telemetry_plugin_revision;
    [FieldOffset(12)]
    public uint ets2_version_major;
    [FieldOffset(16)]
    public uint ets2_version_minor;

    // ***** REVISION 1 ****** //

    [FieldOffset(20)]
    [MarshalAs(UnmanagedType.ByValArray, SizeConst = 4)]
    public byte[] flags;

    // vehicle dynamics

    [FieldOffset(24)]
    public float speed;
    [FieldOffset(28)]
    public float accelerationX;
    [FieldOffset(32)]
    public float accelerationY;
    [FieldOffset(36)]
    public float accelerationZ;


    [FieldOffset(40)]
    public float coordinateX;
    [FieldOffset(44)]
    public float coordinateY;
    [FieldOffset(48)]
    public float coordinateZ;


    [FieldOffset(52)]
    public float rotationX;
    [FieldOffset(56)]
    public float rotationY;
    [FieldOffset(60)]
    public float rotationZ;

    // drivetrain essentials

    [FieldOffset(64)]
    public int gear;
    [FieldOffset(68)]
    public int gears;
    [FieldOffset(72)]
    public int gearRanges;
    [FieldOffset(76)]
    public int gearRangeActive;

    [FieldOffset(80)]
    public float engineRpm;
    [FieldOffset(84)]
    public float engineRpmMax;

    [FieldOffset(88)]
    public float fuel;
    [FieldOffset(92)]
    public float fuelCapacity;
    [FieldOffset(96)]
    public float fuelRate;
    [FieldOffset(100)]
    public float fuelAvgConsumption;

    // user input

    [FieldOffset(104)]
    public float userSteer;
    [FieldOffset(108)]
    public float userThrottle;
    [FieldOffset(112)]
    public float userBrake;
    [FieldOffset(116)]
    public float userClutch;


    [FieldOffset(120)]
    public float gameSteer;
    [FieldOffset(124)]
    public float gameThrottle;
    [FieldOffset(128)]
    public float gameBrake;
    [FieldOffset(132)]
    public float gameClutch;

    // truck & trailer

    [FieldOffset(136)]
    public float truckWeight;
    [FieldOffset(140)]
    public float trailerWeight;

    [FieldOffset(144)]
    public int modelOffset;
    [FieldOffset(148)]
    public int modelLength;

    [FieldOffset(152)]
    public int trailerOffset;
    [FieldOffset(156)]
    public int trailerLength;


    // ***** REVISION 2 ****** //
    [FieldOffset(160)]
    public int timeAbsolute;
    [FieldOffset(164)]
    public int gearsReverse;

    [FieldOffset(168)]
    public float trailerMass;
    [FieldOffset(172)]
    [MarshalAs(UnmanagedType.ByValArray, SizeConst = 64)]
    public byte[] trailerId;
    [FieldOffset(236)]
    [MarshalAs(UnmanagedType.ByValArray, SizeConst = 64)]
    public byte[] trailerName;

    [FieldOffset(300)]
    public int jobIncome;
    [FieldOffset(304)]
    public int jobDeadline;

    [FieldOffset(308)]
    [MarshalAs(UnmanagedType.ByValArray, SizeConst = 64)]
    public byte[] jobCitySource;
    [FieldOffset(372)]
    [MarshalAs(UnmanagedType.ByValArray, SizeConst = 64)]
    public byte[] jobCityDestination;

    [FieldOffset(436)]
    [MarshalAs(UnmanagedType.ByValArray, SizeConst = 64)]
    public byte[] jobCompanySource;
    [FieldOffset(500)]
    [MarshalAs(UnmanagedType.ByValArray, SizeConst = 64)]
    public byte[] jobCompanyDestination;

    // ***** REVISION 3 ****** //
    [FieldOffset(564)]
    public int retarderBrake;
    [FieldOffset(568)]
    public int shifterSlot;
    [FieldOffset(572)]
    public int shifterToggle;
    //[FieldOffset(576)]
    //public int fill;

    [FieldOffset(580)]
    [MarshalAs(UnmanagedType.ByValArray, SizeConst = 24)]
    public byte[] aux;
    [FieldOffset(604)]
    public float airPressure;
    [FieldOffset(608)]
    public float brakeTemperature;
    [FieldOffset(612)]
    public int fuelWarning;
    [FieldOffset(616)]
    public float adblue;
    [FieldOffset(620)]
    public float adblueConsumption;
    [FieldOffset(624)]
    public float oilPressure;
    [FieldOffset(628)]
    public float oilTemperature;
    [FieldOffset(632)]
    public float waterTemperature;
    [FieldOffset(636)]
    public float batteryVoltage;
    [FieldOffset(640)]
    public float lightsDashboard;
    [FieldOffset(644)]
    public float wearEngine;
    [FieldOffset(648)]
    public float wearTransmission;
    [FieldOffset(652)]
    public float wearCabin;
    [FieldOffset(656)]
    public float wearChassis;
    [FieldOffset(660)]
    public float wearWheels;
    [FieldOffset(664)]
    public float wearTrailer;
    [FieldOffset(668)]
    public float truckOdometer;
    [FieldOffset(672)]
    public float cruiseControlSpeed;

    [FieldOffset(676)]
    [MarshalAs(UnmanagedType.ByValArray, SizeConst = 64)]
    public byte[] truckMake;
    [FieldOffset(740)]
    [MarshalAs(UnmanagedType.ByValArray, SizeConst = 64)]
    public byte[] truckMakeId;
    [FieldOffset(804)]
    [MarshalAs(UnmanagedType.ByValArray, SizeConst = 64)]
    public byte[] truckModel;

    // ***** REVISION 4 ****** //
    [FieldOffset(868)]
    public float speedLimit;

    [FieldOffset(872)]
    public float routeDistance;

    [FieldOffset(876)]
    public float routeTime;

    [FieldOffset(880)]
    public float fuelRange;

    [FieldOffset(884)]
    [MarshalAs(UnmanagedType.ByValArray, SizeConst = 24)]
    public float[] gearRatioForward;

    [FieldOffset(980)]
    [MarshalAs(UnmanagedType.ByValArray, SizeConst = 8)]
    public float[] gearRatioReverse;

    [FieldOffset(1012)]
    public float gearRatioDifferential;

    [FieldOffset(1016)]
    public int gearDashboard;

    [FieldOffset(1020)] public byte onJob;
    [FieldOffset(1021)] public byte jobFinished;

    public bool GetBool(Ets2SdkBoolean i)
    {
        if (i == Ets2SdkBoolean.TrailerAttached)
            return flags[1] > 0;
        return aux[(int)i] > 0;
    }
}

当然,在原来的 .net framework 演示项目类中工作。

问题可能出在非 DWORD 对齐数组:link

但据我所知,我无法更改数组的大小(这是 C++ 对象在 SharedMemory 中的映射)。

而且我不知道如何处理这个问题 - 以及为什么该代码在 .net 框架上工作。

有什么建议吗?

最佳答案

我使用了不同的库:link .代码现在可以运行了。

它的工作方式相同,但具有不同的数据结构:

[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi)]
internal struct Ets2TelemetryStructure
{
    public uint time;
    public uint paused;

    public uint ets2_telemetry_plugin_revision;
    public uint ets2_version_major;
    public uint ets2_version_minor;

    // ***** REVISION 1 ****** //

    public short engine_enabled;
    public short trailer_attached;

    public float speed;
    public float accelerationX;
    public float accelerationY;
    public float accelerationZ;

    public float coordinateX;
    public float coordinateY;
    public float coordinateZ;

    public float rotationX;
    public float rotationY;
    public float rotationZ;

    public int gear;
    public int gears;
    public int gearRanges;
    public int gearRangeActive;

    public float engineRpm;
    public float engineRpmMax;

    public float fuel;
    public float fuelCapacity;
    public float fuelRate;
    public float fuelAvgConsumption;

    public float userSteer;
    public float userThrottle;
    public float userBrake;
    public float userClutch;

    public float gameSteer;
    public float gameThrottle;
    public float gameBrake;
    public float gameClutch;

    public float TruckMass;
    public float trailerWeight;

    public int modelOffset;
    public int modelLength;

    public int trailerOffset;
    public int trailerLength;

    public int timeAbsolute;
    public int gearsReverse;

    public float trailerMass;

    [MarshalAs(UnmanagedType.ByValArray, SizeConst = 64)]
    public byte[] trailerId;

    [MarshalAs(UnmanagedType.ByValArray, SizeConst = 64)]
    public byte[] trailerName;

    public int jobIncome;
    public int jobDeadline;

    [MarshalAs(UnmanagedType.ByValArray, SizeConst = 64)]
    public byte[] jobCitySource;
    [MarshalAs(UnmanagedType.ByValArray, SizeConst = 64)]
    public byte[] jobCityDestination;

    [MarshalAs(UnmanagedType.ByValArray, SizeConst = 64)]
    public byte[] jobCompanySource;
    [MarshalAs(UnmanagedType.ByValArray, SizeConst = 64)]
    public byte[] jobCompanyDestination;

    // ***** REVISION 3 ****** //

    public int retarderBrake;
    public int shifterSlot;
    public int shifterToggle;
    public int fill;

    public byte cruiseControl;
    public byte wipers;

    public byte parkBrake;
    public byte motorBrake;

    public byte electricEnabled;
    public byte engineEnabled;

    public byte blinkerLeftActive;
    public byte blinkerRightActive;
    public byte blinkerLeftOn;
    public byte blinkerRightOn;

    public byte lightsParking;
    public byte lightsBeamLow;
    public byte lightsBeamHigh;
    public byte lightsAuxFront;
    public byte lightsAuxRoof;
    public byte lightsBeacon;
    public byte lightsBrake;
    public byte lightsReverse;

    public byte batteryVoltageWarning;
    public byte airPressureWarning;
    public byte airPressureEmergency;
    public byte adblueWarning;
    public byte oilPressureWarning;
    public byte waterTemperatureWarning;

    public float airPressure;
    public float brakeTemperature;
    public float fuelWarning;
    public float adblue;
    public float adblueConsumption;
    public float oilPressure;
    public float oilTemperature;
    public float waterTemperature;
    public float batteryVoltage;
    public float lightsDashboard;
    public float wearEngine;
    public float wearTransmission;
    public float wearCabin;
    public float wearChassis;
    public float wearWheels;
    public float wearTrailer;
    public float truckOdometer;
}

似乎 .net 核心在处理未正确对齐的数组方面存在一些问题 - 在这个库中由两个短变量替换。我认为这是以前使用的库中的错误,例如 Pavel Anikhouski在评论中说。

关于C# System.TypeLoadException : Could not load type because it contains an object field at offset - code from . .net 核心上的 net 框架,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/62490086/

相关文章:

c# - UWP AppServiceConnection 没有获得值(value)

c# - 如果 gzip 文件是通过组合多个 gzip 文件创建的,Chrome 不会解压缩 gzip 文件

c# - 如何防止 .NET 中的 DLL 欺骗

c# - 无法连接kafka集群时无异常

c# - 在.net core 2.0的类库中创建全局缓存

c# - 编译时和运行时?

c# - 使用 RazorEngine 时如何输出原始 html(不是来自 MVC)

C# LINQ 在单次执行中从列表中删除多个对象

.net - IDictionary 到 SelectList?

dll - 在 .Net Core 2.1 (Windows) 中加载 native 库