Refactorization : BenchControl -> Rig
This commit is contained in:
@@ -0,0 +1,231 @@
|
||||
///
|
||||
/// Copyright (c) 2021 Sensus Slovensko a.s.
|
||||
///
|
||||
using System;
|
||||
namespace TBF.Rig.ControlBoard.Uni
|
||||
{
|
||||
public class GeneralData
|
||||
{
|
||||
public const int MessageLen = 303;
|
||||
public const byte MessageCode = (byte)' ';
|
||||
|
||||
/// General data
|
||||
public ulong State; /// bytes 5,6,7,8,9,80,81 = 7 bytes = 56 bits
|
||||
public uint Chyby485;
|
||||
public ulong Vystupy;
|
||||
public uint[] StavDA = new uint[2];
|
||||
public double[] ReferenceFreq = new double[4];
|
||||
public int[] EtPulses = new int[Const.WMsCount + 1]; /// EtPulses[0]=total pulses, EtPulses[1..WMsCount] gated et.pulses for respective WM
|
||||
public int EtPulsesK;
|
||||
public int EtPulses2;
|
||||
public int EtPulses3;
|
||||
public int[] WMeterPuls = new int[Const.WMsCount + 1]; /// WMsCount = 20
|
||||
public double[] ImpulseTime = new double[Const.WMsCount + 1]; /// WMsCount = 20
|
||||
public uint[] RegVStatus = new uint[Const.RVsCount + 1 + 1]; /// RVsCount = 8, posledny rValveStatus[9] je prudovy
|
||||
public float[] RegVMoveTime = new float[Const.RVsCount];
|
||||
public int DivTime;
|
||||
public double Ttime; /// s
|
||||
public double TimeRef; /// s
|
||||
public ulong Vstupy;
|
||||
public Int16[] AnalogInput = new Int16[Const.ADCsCount];
|
||||
public int[] TemperatureRaw = new int[8];
|
||||
|
||||
|
||||
public GeneralData()
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Returns tru when receive data fit the message frame
|
||||
/// </summary>
|
||||
/// <param name="data">Received data</param>
|
||||
/// <param name="cumulativeSums">Cumulative sums of received data bytes</param>
|
||||
/// <param name="rcvdBytesCount">Received bytes count</param>
|
||||
/// <param name="offset">Offset of the message</param>
|
||||
/// <returns>true when frame fits data</returns>
|
||||
public static bool FrameFitsData(byte[] data, int[] cumulativeSums, int rcvdBytesCount, int offset)
|
||||
{
|
||||
if (offset + MessageLen > rcvdBytesCount) return false;
|
||||
|
||||
int checksum = cumulativeSums[offset + MessageLen - 3] - cumulativeSums[offset];
|
||||
|
||||
return data[offset] == Const.STX &&
|
||||
data[offset + 1] == 0x01 &&
|
||||
data[offset + 2] == ((MessageLen - 5) & 0xFF) &&
|
||||
data[offset + 3] == MessageCode &&
|
||||
data[offset + MessageLen - 2] == (checksum & 0xFF) &&
|
||||
data[offset + MessageLen - 1] == ((checksum >> 8) & 0xFF);
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Auxiliary functions
|
||||
/// </summary>
|
||||
/// <param name="data">Received data</param>
|
||||
/// <param name="offs">Offset to the files</param>
|
||||
/// <returns></returns>
|
||||
Int16 GetInt16(byte[] data, int offs) { return BitConverter.ToInt16(data, offs); }
|
||||
UInt16 GetUInt16(byte[] data, int offs) { return BitConverter.ToUInt16(data, offs); }
|
||||
UInt32 GetUInt24(byte[] data, int offs) { return BitConverter.ToUInt32(data, offs) & 0x00FFFFFF; }
|
||||
UInt32 GetUInt32(byte[] data, int offs) { return BitConverter.ToUInt32(data, offs); }
|
||||
UInt64 GetUInt40(byte[] data, int offs) { return BitConverter.ToUInt64(data, offs) & 0x000000FFFFFFFFFF; }
|
||||
UInt64 GetUInt64(byte[] data, int offs) { return BitConverter.ToUInt64(data, offs); }
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Proces received data
|
||||
/// </summary>
|
||||
/// <param name="data">Received data</param>
|
||||
/// <param name="offs">Offset of the message</param>
|
||||
public void UpdateData(byte[] data, int offs)
|
||||
{
|
||||
State = GetUInt40(data, offs + (int)Poz.State) | /// Byte 5,6,7,8,9,80,81
|
||||
((ulong)data[offs + (int)Poz.Stat5] << 40) |
|
||||
((ulong)data[offs + (int)Poz.Stat6] << 48);
|
||||
|
||||
Vystupy = GetUInt64(data, offs + (int)Poz.Vyst); /// Byte 10 .. 17
|
||||
StavDA[1] = GetUInt16(data, offs + (int)Poz.SDA2); /// Byte 18,19
|
||||
Vstupy = GetUInt40(data, offs + (int)Poz.Vst); /// Byte 20,21,22,23,24
|
||||
|
||||
/// A/D converters: Feedback from RV-s and diverters
|
||||
for (int i = 0; i < Const.ADCsCount; i++) /// Byte 25 .. 56
|
||||
{
|
||||
#if DEBUG
|
||||
AnalogInput[Const.ADCsCount - 1 - i] = (short)(11 * (15 - i));
|
||||
#else
|
||||
AnalogInput[Const.ADCsCount - 1 - i] = GetInt16(data, offs + (int)Poz.Analogy + 2 * i);
|
||||
#endif
|
||||
}
|
||||
|
||||
/// Groch temperature meters
|
||||
for (int i = 0; i < 8; i++) /// byte 57 .. 72
|
||||
{
|
||||
TemperatureRaw[i] = GetInt16(data, offs + (int)Poz.Groch + 2 * i);
|
||||
}
|
||||
|
||||
EtPulses[0] = Convert.ToInt32(GetUInt24(data, offs + (int)Poz.Et1));/// Byte 73,74,75
|
||||
EtPulsesK = Convert.ToInt32(GetUInt24(data, offs + (int)Poz.EtK)); /// Byte 76,77,78
|
||||
byte spare1 = data[offs + (int)Poz.spare1]; /// byte 79
|
||||
byte spare2 = data[offs + (int)Poz.spare2]; /// byte 82
|
||||
|
||||
for (int i = 0; i < Const.RVsCount; i++) /// Byte 83 .. 90
|
||||
{
|
||||
RegVStatus[i + 1] = ((uint)data[offs + (int)Poz.RVs + i] >> 3) & 7;
|
||||
}
|
||||
/// 4-20 mA reg. valve
|
||||
uint stavRegQ = (uint)((State >> 16) & 0xFF);
|
||||
RegVStatus[Const.RVsCount + 1] = (stavRegQ >> 4) & 2;
|
||||
|
||||
/// This must preceed processing bytes 91 .. 250 as Ttime is used there
|
||||
uint ttimeRaw = GetUInt32(data, offs + (int)Poz.Ttime); /// Byte 251,252,253,254
|
||||
Ttime = Convert.ToDouble(ttimeRaw) * Const.TimeResolution; /// convert to [s]
|
||||
ImpulseTime[0] = Ttime;
|
||||
|
||||
/// Water meters (pulses count, gated test time, gated etalon pulses count)
|
||||
int ix1 = offs + (int)Poz.CT1; /// Byte 91 .. 250
|
||||
int ix2 = offs + (int)Poz.CTR1;
|
||||
for (int wmNr = 1; wmNr <= Const.WMsCount; wmNr++, ix1 += 6, ix2 += 2)
|
||||
{
|
||||
if ((State & (ulong)StatusP.SynchroMethod) != 0)
|
||||
{
|
||||
ushort pulses = GetUInt16(data, ix2);
|
||||
WMeterPuls[wmNr] = Convert.ToInt32(pulses);
|
||||
EtPulses[wmNr] = (pulses == 0) ? 0 : Convert.ToInt32(GetUInt24(data, ix1));
|
||||
ImpulseTime[wmNr] = (pulses == 0) ? 0 : Const.TimeResolution * Convert.ToDouble(GetUInt24(data, ix1 + 3));
|
||||
}
|
||||
else
|
||||
{
|
||||
WMeterPuls[wmNr] = Convert.ToInt32(GetUInt24(data, ix1));
|
||||
EtPulses[wmNr] = EtPulses[0];
|
||||
ImpulseTime[wmNr] = Ttime;
|
||||
}
|
||||
}
|
||||
|
||||
StavDA[0] = GetUInt16(data, offs + (int)Poz.SDA); /// Byte 255,256
|
||||
byte spare3 = data[offs + (int)Poz.spare3]; /// Byte 257
|
||||
|
||||
/// Impulzy perioda (???)
|
||||
uint[] par1 = new uint[3];
|
||||
uint[] par2 = new uint[3];
|
||||
par2[0] = GetUInt16(data, offs + (int)Poz.Per1); /// Byte 258,259
|
||||
par1[0] = GetUInt16(data, offs + (int)Poz.Per1 + 2); /// Byte 260,261
|
||||
par2[1] = GetUInt16(data, offs + (int)Poz.Per2); /// Byte 262.263
|
||||
par1[1] = GetUInt16(data, offs + (int)Poz.Per2 + 2); /// Byte 264,265
|
||||
par2[2] = GetUInt16(data, offs + (int)Poz.Per3); /// Byte 266,267
|
||||
par1[2] = GetUInt16(data, offs + (int)Poz.Per3 + 2); /// Byte 268,269
|
||||
///
|
||||
ReferenceFreq[0] = (par2[0] != 0) ? (5.0f * par1[0] / par2[0]) : 0.0f;
|
||||
ReferenceFreq[1] = ReferenceFreq[2] = ReferenceFreq[3] = 0;
|
||||
///
|
||||
if ((State & (ulong)StatusP.TestWithRefFlowmtr) != 0 && (State & (ulong)StatusP.FlowmtrNrMask) == 0)
|
||||
{
|
||||
/// Measurement with parallel flowmeters
|
||||
if ((State & (ulong)StatusP.Flowmtr1Active) != 0)
|
||||
{
|
||||
ReferenceFreq[1] = ReferenceFreq[0];
|
||||
}
|
||||
|
||||
if ((State & (ulong)StatusP.Flowmtr2Active) != 0)
|
||||
{
|
||||
ReferenceFreq[2] = (par2[1] != 0) ? (5.0f * par1[1] / par2[1]) : 0.0f;
|
||||
}
|
||||
|
||||
if ((State & (ulong)StatusP.Flowmtr3Active) != 0)
|
||||
{
|
||||
ReferenceFreq[3] = (par2[2] != 0) ? (5.0f * par1[2] / par2[2]) : 0.0f;
|
||||
}
|
||||
|
||||
ReferenceFreq[0] = ReferenceFreq[1] + ReferenceFreq[2] + ReferenceFreq[3];
|
||||
}
|
||||
|
||||
DivTime = Const.DivTimeResolution * data[offs + (int)Poz.CasKl]; /// Byte 271
|
||||
byte spare4 = data[offs + (int)Poz.spare4]; /// Byte 272
|
||||
Chyby485 = GetUInt16(data, offs + (int)Poz.Chyb485); /// Byte 273, 274 !!!!!!!!!!!!!!!
|
||||
uint timeRefRaw = GetUInt24(data, offs + (int)Poz.Tim2); /// Byte 274,275,276 !!!!!!!!!!!!!!!
|
||||
TimeRef = Convert.ToDouble(timeRefRaw) / 1000.0; /// convert to [s]
|
||||
|
||||
for (int i = 0; i < Const.RVsCount; i++) /// Byte 278 .. 293
|
||||
{
|
||||
RegVMoveTime[i] = 10 * GetUInt16(data, offs + (int)Poz.CasKoh + 2*i);
|
||||
}
|
||||
|
||||
EtPulses2 = Convert.ToInt32(GetUInt24(data, offs + (int)Poz.ETX2)); /// Byte 294,295,296
|
||||
EtPulses3 = Convert.ToInt32(GetUInt24(data, offs + (int)Poz.ETX3)); /// Byte 297,298.299 !!!!!!!!!!!!!!!
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Byte positions in rcvdData buffer
|
||||
/// </summary>
|
||||
public enum Poz : int
|
||||
{
|
||||
State = 5, /// 5 .. 9
|
||||
Vyst = State + 5, /// 10 .. 17
|
||||
SDA2 = Vyst + 8, /// 18,19
|
||||
Vst = SDA2 + 2, /// 20 .. 24
|
||||
Analogy = Vst + 5, /// 25 .. 56
|
||||
Groch = Analogy + 2 * Const.ADCsCount, /// 57 (16 analog inputs)
|
||||
Et1 = Groch + 16, /// 73,74,75
|
||||
EtK = Et1 + 3, /// 76,77,78
|
||||
spare1 = EtK + 3, /// 79
|
||||
Stat5 = spare1 + 1, /// 80
|
||||
Stat6 = Stat5 + 1, /// 81
|
||||
spare2 = Stat6 + 1, /// 82
|
||||
RVs = spare2 + 1, /// 83
|
||||
CT1 = RVs + 8, /// 91
|
||||
CTR1 = CT1 + 6 * Const.WMsCount, /// 211
|
||||
Ttime = CTR1 + 2 * Const.WMsCount, /// 251
|
||||
SDA = Ttime + 4, /// 255
|
||||
spare3 = SDA + 2, /// 257
|
||||
Per1 = spare3 + 1, /// 258
|
||||
Per2 = Per1 + 4, /// 262
|
||||
Per3 = Per2 + 4, /// 266
|
||||
CasKl = Per3 + 5, /// 271
|
||||
spare4 = CasKl + 1, /// 272
|
||||
Chyb485 = spare4 + 1, /// 273
|
||||
Tim2 = Chyb485 + 1, /// 274
|
||||
CasKoh = Tim2 + 4, /// 278
|
||||
ETX2 = CasKoh + 2 * Const.RVsCount, /// 294
|
||||
ETX3 = ETX2 + 3, /// 297
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user