2017-02-25 update 2 Endian Fix

This commit is contained in:
parallelbgls
2017-02-25 10:48:19 +08:00
parent 84e5be1659
commit 962f7a80d8
10 changed files with 100 additions and 33 deletions

View File

@@ -49,8 +49,8 @@ namespace Modbus.Net.Modbus
AddressTranslator = new AddressTranslatorModbus(); AddressTranslator = new AddressTranslatorModbus();
} }
public override bool GetLittleEndian => Wrapper[typeof (ReadDataModbusProtocal)].IsLittleEndian; public override Endian GetLittleEndian => Wrapper[typeof (ReadDataModbusProtocal)].IsLittleEndian;
public override bool SetLittleEndian => Wrapper[typeof (WriteDataModbusProtocal)].IsLittleEndian; public override Endian SetLittleEndian => Wrapper[typeof (WriteDataModbusProtocal)].IsLittleEndian;
protected string ConnectionStringIp protected string ConnectionStringIp
{ {

View File

@@ -15,8 +15,8 @@ namespace Modbus.Net.OPC
Wrapper = new OpcDaProtocal(ConnectionString); Wrapper = new OpcDaProtocal(ConnectionString);
} }
public override bool GetLittleEndian => Wrapper[typeof (ReadRequestOpcProtocal)].IsLittleEndian; public override Endian GetLittleEndian => Wrapper[typeof (ReadRequestOpcProtocal)].IsLittleEndian;
public override bool SetLittleEndian => Wrapper[typeof (WriteRequestOpcProtocal)].IsLittleEndian; public override Endian SetLittleEndian => Wrapper[typeof (WriteRequestOpcProtocal)].IsLittleEndian;
public override void SetConnectionType(int connectionType) public override void SetConnectionType(int connectionType)
{ {

View File

@@ -20,12 +20,12 @@ namespace Modbus.Net.Siemens
_com = com; _com = com;
} }
public override byte[] SendReceive(bool isLittleEndian, params object[] content) public override byte[] SendReceive(Endian isLittleEndian, params object[] content)
{ {
return AsyncHelper.RunSync(() => SendReceiveAsync(isLittleEndian, content)); return AsyncHelper.RunSync(() => SendReceiveAsync(isLittleEndian, content));
} }
public override async Task<byte[]> SendReceiveAsync(bool isLittleEndian, params object[] content) public override async Task<byte[]> SendReceiveAsync(Endian isLittleEndian, params object[] content)
{ {
if (ProtocalLinker == null || !ProtocalLinker.IsConnected) if (ProtocalLinker == null || !ProtocalLinker.IsConnected)
{ {

View File

@@ -41,12 +41,12 @@ namespace Modbus.Net.Siemens
_connectTryCount = 0; _connectTryCount = 0;
} }
public override byte[] SendReceive(bool isLittleEndian, params object[] content) public override byte[] SendReceive(Endian isLittleEndian, params object[] content)
{ {
return AsyncHelper.RunSync(() => SendReceiveAsync(isLittleEndian, content)); return AsyncHelper.RunSync(() => SendReceiveAsync(isLittleEndian, content));
} }
public override async Task<byte[]> SendReceiveAsync(bool isLittleEndian, params object[] content) public override async Task<byte[]> SendReceiveAsync(Endian isLittleEndian, params object[] content)
{ {
if (ProtocalLinker == null || !ProtocalLinker.IsConnected) if (ProtocalLinker == null || !ProtocalLinker.IsConnected)
{ {

View File

@@ -91,8 +91,8 @@ namespace Modbus.Net.Siemens
AddressTranslator = new AddressTranslatorSiemens(); AddressTranslator = new AddressTranslatorSiemens();
} }
public override bool GetLittleEndian => Wrapper[typeof (ReadRequestSiemensProtocal)].IsLittleEndian; public override Endian GetLittleEndian => Wrapper[typeof (ReadRequestSiemensProtocal)].IsLittleEndian;
public override bool SetLittleEndian => Wrapper[typeof (WriteRequestSiemensProtocal)].IsLittleEndian; public override Endian SetLittleEndian => Wrapper[typeof (WriteRequestSiemensProtocal)].IsLittleEndian;
protected string ConnectionStringIp protected string ConnectionStringIp
{ {

View File

@@ -257,13 +257,17 @@ namespace Modbus.Net
{ {
PlcValue = PlcValue =
Convert.ToDouble( Convert.ToDouble(
BaseUtility.GetLittleEndian BaseUtility.GetLittleEndian == Endian.LittleEndianLsb
? ValueHelper.Instance.GetValue(datas, ref localMainPos, ref localSubPos, ? ValueHelper.Instance.GetValue(datas, ref localMainPos, ref localSubPos,
address.DataType) address.DataType)
.ToString() .ToString()
: BigEndianValueHelper.Instance.GetValue(datas, ref localMainPos, : BaseUtility.GetLittleEndian == Endian.BigEndianLsb
ref localSubPos, ? BigEndianValueHelper.Instance.GetValue(datas, ref localMainPos,
address.DataType))*address.Zoom, ref localSubPos,
address.DataType)
: BigEndianMsbValueHelper.Instance.GetValue(datas, ref localMainPos,
ref localSubPos,
address.DataType))*address.Zoom,
UnitExtend = address.UnitExtend UnitExtend = address.UnitExtend
}); });
} }
@@ -374,9 +378,11 @@ namespace Modbus.Net
BigEndianValueHelper.Instance.ByteLength[ BigEndianValueHelper.Instance.ByteLength[
communicateAddress.DataType.FullName])); communicateAddress.DataType.FullName]));
var valueHelper = BaseUtility.SetLittleEndian var valueHelper = BaseUtility.SetLittleEndian == Endian.LittleEndianLsb
? ValueHelper.Instance ? ValueHelper.Instance
: BigEndianValueHelper.Instance; : BaseUtility.SetLittleEndian == Endian.BigEndianLsb
? BigEndianValueHelper.Instance
: BigEndianMsbValueHelper.Instance;
//如果设备本身能获取到数据但是没有数据 //如果设备本身能获取到数据但是没有数据
var datas = datasReturn; var datas = datasReturn;

View File

@@ -72,7 +72,7 @@ namespace Modbus.Net
/// <param name="isLittleEndian">是否是小端格式</param> /// <param name="isLittleEndian">是否是小端格式</param>
/// <param name="content">写入的内容,使用对象数组描述</param> /// <param name="content">写入的内容,使用对象数组描述</param>
/// <returns>从设备获取的字节流</returns> /// <returns>从设备获取的字节流</returns>
public virtual byte[] SendReceive(bool isLittleEndian, params object[] content) public virtual byte[] SendReceive(Endian isLittleEndian, params object[] content)
{ {
return AsyncHelper.RunSync(() => SendReceiveAsync(isLittleEndian, content)); return AsyncHelper.RunSync(() => SendReceiveAsync(isLittleEndian, content));
} }
@@ -83,7 +83,7 @@ namespace Modbus.Net
/// <param name="isLittleEndian">是否是小端格式</param> /// <param name="isLittleEndian">是否是小端格式</param>
/// <param name="content">写入的内容,使用对象数组描述</param> /// <param name="content">写入的内容,使用对象数组描述</param>
/// <returns>从设备获取的字节流</returns> /// <returns>从设备获取的字节流</returns>
public virtual async Task<byte[]> SendReceiveAsync(bool isLittleEndian, params object[] content) public virtual async Task<byte[]> SendReceiveAsync(Endian isLittleEndian, params object[] content)
{ {
if (ProtocalLinker == null || !ProtocalLinker.IsConnected) if (ProtocalLinker == null || !ProtocalLinker.IsConnected)
{ {

View File

@@ -3,8 +3,17 @@ using System.Collections.Generic;
using System.Linq; using System.Linq;
using System.Threading.Tasks; using System.Threading.Tasks;
public enum Endian
{
LittleEndianLsb,
BigEndianLsb,
BigEndianMsb
}
namespace Modbus.Net namespace Modbus.Net
{ {
/// <summary> /// <summary>
/// 基础Api入口 /// 基础Api入口
/// </summary> /// </summary>
@@ -33,12 +42,12 @@ namespace Modbus.Net
/// <summary> /// <summary>
/// 获取协议是否遵循小端格式 /// 获取协议是否遵循小端格式
/// </summary> /// </summary>
public abstract bool GetLittleEndian { get; } public abstract Endian GetLittleEndian { get; }
/// <summary> /// <summary>
/// 设置协议是否遵循小端格式 /// 设置协议是否遵循小端格式
/// </summary> /// </summary>
public abstract bool SetLittleEndian { get; } public abstract Endian SetLittleEndian { get; }
/// <summary> /// <summary>
/// 设备是否已经连接 /// 设备是否已经连接
@@ -108,9 +117,22 @@ namespace Modbus.Net
var getReturnValue = await GetDatasAsync(startAddress, var getReturnValue = await GetDatasAsync(startAddress,
(int) Math.Ceiling(bCount*getTypeAndCount.Value)); (int) Math.Ceiling(bCount*getTypeAndCount.Value));
var getBytes = getReturnValue; var getBytes = getReturnValue;
return GetLittleEndian switch (GetLittleEndian)
? ValueHelper.Instance.ByteArrayToObjectArray(getBytes, getTypeAndCount) {
: BigEndianValueHelper.Instance.ByteArrayToObjectArray(getBytes, getTypeAndCount); case Endian.LittleEndianLsb:
{
return ValueHelper.Instance.ByteArrayToObjectArray(getBytes, getTypeAndCount);
}
case Endian.BigEndianLsb:
{
return BigEndianValueHelper.Instance.ByteArrayToObjectArray(getBytes, getTypeAndCount);
}
case Endian.BigEndianMsb:
{
return BigEndianMsbValueHelper.Instance.ByteArrayToObjectArray(getBytes, getTypeAndCount);
}
}
return null;
} }
catch (Exception) catch (Exception)
{ {
@@ -185,9 +207,22 @@ namespace Modbus.Net
select (int) Math.Ceiling(bCount*getTypeAndCount.Value)).Sum(); select (int) Math.Ceiling(bCount*getTypeAndCount.Value)).Sum();
var getReturnValue = await GetDatasAsync(startAddress, bAllCount); var getReturnValue = await GetDatasAsync(startAddress, bAllCount);
var getBytes = getReturnValue; var getBytes = getReturnValue;
return GetLittleEndian switch (GetLittleEndian)
? ValueHelper.Instance.ByteArrayToObjectArray(getBytes, translateTypeAndCount) {
: BigEndianValueHelper.Instance.ByteArrayToObjectArray(getBytes, translateTypeAndCount); case Endian.LittleEndianLsb:
{
return ValueHelper.Instance.ByteArrayToObjectArray(getBytes, translateTypeAndCount);
}
case Endian.BigEndianLsb:
{
return BigEndianValueHelper.Instance.ByteArrayToObjectArray(getBytes, translateTypeAndCount);
}
case Endian.BigEndianMsb:
{
return BigEndianMsbValueHelper.Instance.ByteArrayToObjectArray(getBytes, translateTypeAndCount);
}
}
return null;
} }
catch (Exception) catch (Exception)
{ {

View File

@@ -10,11 +10,11 @@ namespace Modbus.Net
/// <summary> /// <summary>
/// 是否为小端格式 /// 是否为小端格式
/// </summary> /// </summary>
public bool IsLittleEndian { get; protected set; } = false; public Endian IsLittleEndian { get; protected set; } = Endian.BigEndianLsb;
/// <summary> /// <summary>
/// 从输入结构格式化 /// 从输入结构格式化
/// </summary> /// </summary>s
/// <param name="message">结构化的输入数据</param> /// <param name="message">结构化的输入数据</param>
/// <returns>格式化后的字节流</returns> /// <returns>格式化后的字节流</returns>
public abstract byte[] Format(IInputStruct message); public abstract byte[] Format(IInputStruct message);
@@ -43,11 +43,24 @@ namespace Modbus.Net
/// <param name="isLittleEndian">是否是小端格式</param> /// <param name="isLittleEndian">是否是小端格式</param>
/// <param name="contents">对象数组</param> /// <param name="contents">对象数组</param>
/// <returns>字节数组</returns> /// <returns>字节数组</returns>
public static byte[] TranslateContent(bool isLittleEndian, params object[] contents) public static byte[] TranslateContent(Endian isLittleEndian, params object[] contents)
{ {
return isLittleEndian switch (isLittleEndian)
? ValueHelper.Instance.ObjectArrayToByteArray(contents) {
: BigEndianValueHelper.Instance.ObjectArrayToByteArray(contents); case Endian.LittleEndianLsb:
{
return ValueHelper.Instance.ObjectArrayToByteArray(contents);
}
case Endian.BigEndianLsb:
{
return BigEndianValueHelper.Instance.ObjectArrayToByteArray(contents);
}
case Endian.BigEndianMsb:
{
return BigEndianMsbValueHelper.Instance.ObjectArrayToByteArray(contents);
}
}
return null;
} }
} }

View File

@@ -822,7 +822,7 @@ namespace Modbus.Net
/// <param name="subPos">设置位置</param> /// <param name="subPos">设置位置</param>
/// <param name="setBit">设置bit大小true为1false为0</param> /// <param name="setBit">设置bit大小true为1false为0</param>
/// <returns></returns> /// <returns></returns>
public byte SetBit(byte number, int subPos, bool setBit) protected byte SetBit(byte number, int subPos, bool setBit)
{ {
var creation = 0; var creation = 0;
if (setBit) if (setBit)
@@ -1013,6 +1013,19 @@ namespace Modbus.Net
public class BigEndianMsbValueHelper : BigEndianValueHelper public class BigEndianMsbValueHelper : BigEndianValueHelper
{ {
private static BigEndianValueHelper _bigEndianInstance;
protected BigEndianMsbValueHelper()
{
}
protected override ValueHelper _Instance => _bigEndianInstance;
protected new bool LittleEndian => false;
public new static BigEndianValueHelper Instance
=> _bigEndianInstance ?? (_bigEndianInstance = new BigEndianMsbValueHelper());
public override bool GetBit(byte[] number, ref int pos, ref int subPos) public override bool GetBit(byte[] number, ref int pos, ref int subPos)
{ {
if (subPos < 0 && subPos > 7) throw new IndexOutOfRangeException(); if (subPos < 0 && subPos > 7) throw new IndexOutOfRangeException();