/// /// Copyright (c) 2018 Sensus Slovensko a.s. /// using System; namespace TBF.BenchControl.TestMethods.iPerlCommunication.iPerlHead { public class CalibrationStructV4 { public static readonly int Length = 37; public Byte Version; public MeterType MeterType; public UInt16 Calibration; public VolumeUnits VolumeUnits; public FlowArrow FlowArrow; public UInt16 FWVersion; public UInt16[] TargetField; public UInt16 RecipMeanCurrent; public UInt16 ThresholdVolume; public UInt16 ThresholdTime; public UInt16 FlowActivationThr; public UInt16 VolumeArrowThr; public UInt32 CalibrationTime; public ulong SerialNumber; public MeterSealed MeterSealed; public UInt16 CalibrationLNA; public byte CheckSum; public CalibrationStructV4() { TargetField = new UInt16[3]; } public byte[] ToByteArray() { byte[] result = new byte[Length]; result[0] = Version; result[1] = (byte)MeterType; result[2] = (byte)(Calibration & 0x00FF); result[3] = (byte)((Calibration >> 8) & 0x00FF); result[4] = (byte)VolumeUnits; result[5] = (byte)FlowArrow; result[6] = (byte)(FWVersion & 0x00FF); result[7] = (byte)((FWVersion >> 8) & 0x00FF); result[8] = (byte)( TargetField[0] & 0x00FF); result[9] = (byte)((TargetField[0] >> 8) & 0x00FF); result[10] = (byte)( TargetField[1] & 0x00FF); result[11] = (byte)((TargetField[1] >> 8) & 0x00FF); result[12] = (byte)( TargetField[2] & 0x00FF); result[13] = (byte)((TargetField[2] >> 8) & 0x00FF); result[14] = (byte)(RecipMeanCurrent & 0x00FF); result[15] = (byte)((RecipMeanCurrent >> 8) & 0x00FF); result[16] = (byte)(ThresholdVolume & 0x00FF); result[17] = (byte)((ThresholdVolume >> 8) & 0x00FF); result[18] = (byte)(ThresholdTime & 0x00FF); result[19] = (byte)((ThresholdTime >> 8) & 0x00FF); result[20] = (byte)(FlowActivationThr & 0x00FF); result[21] = (byte)((FlowActivationThr >> 8) & 0x00FF); result[22] = (byte)(VolumeArrowThr & 0x00FF); result[23] = (byte)((VolumeArrowThr >> 8) & 0x00FF); result[24] = (byte)(CalibrationTime & 0x000000FF); result[25] = (byte)((CalibrationTime >> 8) & 0x000000FF); result[26] = (byte)((CalibrationTime >> 16) & 0x000000FF); result[27] = (byte)((CalibrationTime >> 24) & 0x000000FF); result[28] = (byte)(SerialNumber & 0x00000000000000FF); result[29] = (byte)((SerialNumber >> 8) & 0x00000000000000FF); result[30] = (byte)((SerialNumber >> 16) & 0x00000000000000FF); result[31] = (byte)((SerialNumber >> 24) & 0x00000000000000FF); result[32] = (byte)((SerialNumber >> 32) & 0x00000000000000FF); result[33] = (byte)MeterSealed; result[34] = (byte)(CalibrationLNA & 0x00FF); result[35] = (byte)((CalibrationLNA >> 8) & 0x00FF); result[36] = CheckSum; return result; } /// /// Create a calibration structure from a complete byte array /// /// A complete byte array data /// CalibrationStructV4 or null when byte array was not complete public static CalibrationStructV4 FromByteArray(byte[] data) { if (data.Length != Length) return null; CalibrationStructV4 result = new CalibrationStructV4(); result.Version = data[0]; result.MeterType = (MeterType)data[1]; result.Calibration = (UInt16)(data[2] + 256 * data[3]); result.VolumeUnits = (VolumeUnits)data[4]; result.FlowArrow = (FlowArrow)data[5]; result.FWVersion = (UInt16)(data[6] + 256 * data[7]); result.TargetField[0] = (UInt16)(data[8] + 256 * data[9]); result.TargetField[1] = (UInt16)(data[10] + 256 * data[11]); result.TargetField[2] = (UInt16)(data[12] + 256 * data[13]); result.RecipMeanCurrent = (UInt16)(data[14] + 256 * data[15]); result.ThresholdVolume = (UInt16)(data[16] + 256 * data[17]); result.ThresholdTime = (UInt16)(data[18] + 256 * data[19]); result.FlowActivationThr = (UInt16)(data[20] + 256 * data[21]); result.VolumeArrowThr = (UInt16)(data[22] + 256 * data[23]); result.CalibrationTime = (((UInt32)data[27] * 256 + data[26]) * 256 + data[25]) * 256 + data[24]; result.SerialNumber = ((((UInt64)data[32] * 256 + data[31]) * 256 + data[30]) * 256 + data[29]) * 256 + data[28]; result.MeterSealed = (MeterSealed)data[33]; result.CalibrationLNA = (UInt16)(data[34] + 256 * data[35]); result.CheckSum = data[36]; return result; } /// /// Update the calibration structure from an incomplete byte array /// /// Byte array data /// Offset of byte array data in CalibrationStructV2 /// true when successful, false when data are not appropriate public bool Update(byte[] data, int offset) { if ((data.Length == 2) && (offset == 2)) { /// Data containing iPerl calibration factor Calibration = (UInt16)(data[0] + 256 * data[1]); return true; } else if ((data.Length == 2) && (offset == 34)) { /// Data containing iPerl calibration factor CalibrationLNA = (UInt16)(data[0] + 256 * data[1]); return true; } else if ((data.Length == Length) && (offset == 0)) { /// Data containing a complete CalibrationStruct Version = data[0]; MeterType = (MeterType)data[1]; Calibration = (UInt16)(data[2] + 256 * data[3]); VolumeUnits = (VolumeUnits)data[4]; FlowArrow = (FlowArrow)data[5]; FWVersion = (UInt16)(data[6] + 256 * data[7]); TargetField[0] = (UInt16)(data[8] + 256 * data[9]); TargetField[1] = (UInt16)(data[10] + 256 * data[11]); TargetField[2] = (UInt16)(data[12] + 256 * data[13]); RecipMeanCurrent = (UInt16)(data[14] + 256 * data[15]); ThresholdVolume = (UInt16)(data[16] + 256 * data[17]); ThresholdTime = (UInt16)(data[18] + 256 * data[19]); FlowActivationThr = (UInt16)(data[20] + 256 * data[21]); VolumeArrowThr = (UInt16)(data[22] + 256 * data[23]); CalibrationTime = (((UInt32)data[27] * 256 + data[26]) * 256 + data[25]) * 256 + data[24]; SerialNumber = ((((UInt64)data[32] * 256 + data[31]) * 256 + data[30]) * 256 + data[29]) * 256 + data[28]; MeterSealed = (MeterSealed)data[33]; CalibrationLNA = (UInt16)(data[34] + 256 * data[35]); CheckSum = data[36]; return true; } else return false; } public string FWVersionStr() { int d1 = (FWVersion >> 8) & 0x000F; int d2 = (FWVersion >> 12) & 0x000F; int d3 = (FWVersion >> 4) & 0x000F; int d4 = FWVersion & 0x000F; return string.Format("{0}.{1}{2}{3}", d1, d2, d3, d4); } public override string ToString() { return string.Format("Calibration: V{0} Type={1} Cal={2} Units={3} FlowArrow.{4} FW={5} Hi={6} Norm={7} Low={8} RMC={9} ThrVol={10} ThrTime={11} FlActThr={12} VolArrThr={13} CalTm={14} SN={15} MeterSealed={16} CalLNA={17} Chksum={18}", Version, MeterType, Calibration, VolumeUnits, FlowArrow, FWVersion, TargetField[0], TargetField[1], TargetField[2], RecipMeanCurrent, ThresholdVolume, ThresholdTime, FlowActivationThr, VolumeArrowThr, CalibrationTime, SerialNumber, MeterSealed, CalibrationLNA, CheckSum.ToString("X2")); } } }