CUST: - FwUpdateSw: - LUT check and logging
Common/.../GenesisFile/MeterLutFile: - LUT file analyze function
This commit is contained in:
@@ -1,6 +1,8 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Text;
|
||||
using Xylem.Common.Logic.ProductionOrderCore.OrderData;
|
||||
using Xylem.Common.Utils.Crc16Ccitt;
|
||||
|
||||
namespace Xylem.Common.Hardware.WaterMeter.Genesis.GenesisFile
|
||||
{
|
||||
@@ -93,6 +95,11 @@ namespace Xylem.Common.Hardware.WaterMeter.Genesis.GenesisFile
|
||||
/// </summary>
|
||||
public UInt16 CalculatedCrc;
|
||||
|
||||
/// <summary>
|
||||
/// FileCRC and calculated CRC are different
|
||||
/// </summary>
|
||||
public Boolean CrcError;
|
||||
|
||||
/// <summary>
|
||||
/// Validation of LUT file
|
||||
/// </summary>
|
||||
@@ -107,5 +114,48 @@ namespace Xylem.Common.Hardware.WaterMeter.Genesis.GenesisFile
|
||||
/// Meter size
|
||||
/// </summary>
|
||||
public MeterSize MeterSize;
|
||||
|
||||
/// <summary>
|
||||
/// Verifies the LUT format based on its contents
|
||||
/// </summary>
|
||||
/// <returns>true if valid</returns>
|
||||
public Boolean ValidateLutFormat()
|
||||
{
|
||||
IsValid = false;
|
||||
|
||||
if (BinData == null || BinData.Count < SizeLutFile)
|
||||
return false;
|
||||
// extract the identifier and check, if this is a LUT file
|
||||
StrLutFileId = Encoding.UTF8.GetString(BinData.ToArray(), MeterLutFile.IndexLutFileId,
|
||||
MeterLutFile.IndexDataLength);
|
||||
if (StrLutFileId != MeterLutFile.StrLutMeterFileId)
|
||||
return false;
|
||||
|
||||
MeterSize = (MeterSize)BinData[MeterLutFile.IndexMeterSize];
|
||||
FileCrc = (UInt16)(BinData[MeterLutFile.IndexCrc] +
|
||||
(BinData[MeterLutFile.IndexCrc + 1] << 8));
|
||||
Version = (UInt16)(BinData[MeterLutFile.IndexVersion] +
|
||||
(BinData[MeterLutFile.IndexVersion + 1] << 8));
|
||||
DataLength = (UInt32)(BinData[MeterLutFile.IndexDataLength]
|
||||
+ (BinData[MeterLutFile.IndexDataLength + 1] << 8)
|
||||
+ (BinData[MeterLutFile.IndexDataLength + 2] << 16)
|
||||
+ (BinData[MeterLutFile.IndexDataLength + 3] << 24));
|
||||
// calculate CRC and compare this with the file CRC
|
||||
var entireFile = new List<Byte>();
|
||||
entireFile.AddRange(BinData);
|
||||
var payload = new List<Byte>();
|
||||
payload.AddRange(entireFile.GetRange(MeterLutFile.IndexVersion,
|
||||
MeterLutFile.LutFileDataLength + MeterLutFile.LengthVersion));
|
||||
CalculatedCrc = Crc16Ccitt.CalculateMsb1021(payload.ToArray());
|
||||
if (CalculatedCrc != FileCrc)
|
||||
{
|
||||
CrcError = true;
|
||||
return false;
|
||||
}
|
||||
|
||||
CrcError = false;
|
||||
IsValid = true;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2,7 +2,6 @@
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading;
|
||||
using Xylem.Common.Hardware.WaterMeter.Genesis.GenesisCore;
|
||||
using Xylem.Common.Hardware.WaterMeter.Genesis.GenesisCore.Consts;
|
||||
@@ -10,7 +9,6 @@ using Xylem.Common.Hardware.WaterMeter.Genesis.GenesisFile.Consts;
|
||||
using Xylem.Common.Hardware.WaterMeter.Genesis.Registers;
|
||||
using Xylem.Common.Hardware.WaterMeter.WaterMeterCore.Consts;
|
||||
using Xylem.Common.Logic.ProductionOrderCore.OrderData;
|
||||
using Xylem.Common.Utils.Crc16Ccitt;
|
||||
using Xylem.Common.Utils.ProcessExec;
|
||||
using Xylem.Common.Utils.ProcessExec.EventArguments;
|
||||
|
||||
@@ -483,6 +481,9 @@ namespace Xylem.Common.Hardware.WaterMeter.Genesis.GenesisFile
|
||||
/// <remarks date="2022-Feb-25" author="Thomas Wiedebusch">
|
||||
/// - Initial
|
||||
/// </remarks>
|
||||
/// <remarks date="2023-Nov-13" author="Thomas Wiedebusch">
|
||||
/// - LUT file validation exported to <see cref="MeterLutFile.ValidateLutFormat"/>
|
||||
/// </remarks>
|
||||
private Boolean ValidateLutFile()
|
||||
{
|
||||
// check if LUT file contains data
|
||||
@@ -492,38 +493,15 @@ namespace Xylem.Common.Hardware.WaterMeter.Genesis.GenesisFile
|
||||
return false;
|
||||
}
|
||||
|
||||
LutFile.IsValid = false;
|
||||
// extract the identifier and check, if this is a LUT file
|
||||
LutFile.StrLutFileId = Encoding.UTF8.GetString(LutFile.BinData.ToArray(), MeterLutFile.IndexLutFileId,
|
||||
MeterLutFile.IndexDataLength);
|
||||
if (LutFile.StrLutFileId != MeterLutFile.StrLutMeterFileId)
|
||||
return false;
|
||||
|
||||
LutFile.MeterSize = (MeterSize)LutFile.BinData[MeterLutFile.IndexMeterSize];
|
||||
LutFile.FileCrc = (UInt16)(LutFile.BinData[MeterLutFile.IndexCrc] +
|
||||
(LutFile.BinData[MeterLutFile.IndexCrc + 1] << 8));
|
||||
LutFile.Version = (UInt16)(LutFile.BinData[MeterLutFile.IndexVersion] +
|
||||
(LutFile.BinData[MeterLutFile.IndexVersion + 1] << 8));
|
||||
LutFile.DataLength = (UInt32)(LutFile.BinData[MeterLutFile.IndexDataLength]
|
||||
+ (LutFile.BinData[MeterLutFile.IndexDataLength + 1] << 8)
|
||||
+ (LutFile.BinData[MeterLutFile.IndexDataLength + 2] << 16)
|
||||
+ (LutFile.BinData[MeterLutFile.IndexDataLength + 3] << 24));
|
||||
// calculate CRC and compare this with the file CRC
|
||||
var entireFile = new List<Byte>();
|
||||
entireFile.AddRange(LutFile.BinData);
|
||||
var payload = new List<Byte>();
|
||||
payload.AddRange(entireFile.GetRange(MeterLutFile.IndexVersion,
|
||||
MeterLutFile.LutFileDataLength + MeterLutFile.LengthVersion));
|
||||
var calculatedCrc = Crc16Ccitt.CalculateMsb1021(payload.ToArray());
|
||||
if (calculatedCrc != LutFile.FileCrc)
|
||||
// Take the file content to validate the format based
|
||||
var lutFileFormatValid = LutFile.ValidateLutFormat();
|
||||
if (LutFile.CrcError)
|
||||
{
|
||||
ErrorMessage = "CRC mismatch!";
|
||||
return false;
|
||||
}
|
||||
|
||||
LutFile.CalculatedCrc = calculatedCrc;
|
||||
LutFile.IsValid = true;
|
||||
return true;
|
||||
return lutFileFormatValid;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
||||
@@ -24,6 +24,7 @@ using Xylem.Common.Hardware.WaterMeter.Genesis.GenesisPwd;
|
||||
using Xylem.Common.Hardware.WaterMeter.Genesis.Registers;
|
||||
using Xylem.Common.Hardware.WaterMeter.Genesis.Registers.DataTypes;
|
||||
using Xylem.Common.Hardware.WaterMeter.WaterMeterCore;
|
||||
using Xylem.Common.Logic.ProductionOrderCore.OrderData;
|
||||
using Xylem.Common.Utils.Logging;
|
||||
using Xylem.Common.Utils.ProcessExec;
|
||||
using Xylem.Common.Utils.ProcessExec.EventArguments;
|
||||
@@ -53,7 +54,6 @@ namespace Xylem.ServiceFwUpdate.Ui.ServiceFwUpdateSw
|
||||
private readonly MeterBatch _meterBatch;
|
||||
private Byte[] _fwUpdateSafePwdFile;
|
||||
private MeterLutFile _fwUpdateSafeLutFile;
|
||||
private MeterLutFile _meterLutFile;
|
||||
private String _passwordLvl8;
|
||||
private String _skeletonKey;
|
||||
|
||||
@@ -1689,7 +1689,7 @@ namespace Xylem.ServiceFwUpdate.Ui.ServiceFwUpdateSw
|
||||
/// <summary>
|
||||
/// Logging of LUT file read from meter.
|
||||
/// </summary>
|
||||
/// <remarks date="2023-Nov-10" author="Thomas Wiedebusch">
|
||||
/// <remarks date="2023-Nov-13" author="Thomas Wiedebusch">
|
||||
/// - Initial.
|
||||
/// </remarks>
|
||||
private Boolean ReadLogAndCompareMeterLutFile()
|
||||
@@ -1702,66 +1702,56 @@ namespace Xylem.ServiceFwUpdate.Ui.ServiceFwUpdateSw
|
||||
{
|
||||
// Read the meter LUT file
|
||||
var meterFile = new MeterFile(_currentGenesis);
|
||||
retVal = meterFile.ReadMeterFile(MeterLutFile.StrLutMeterFileName, out var meterLutFile);
|
||||
var meterLutFile = new MeterLutFile();
|
||||
retVal = meterFile.ReadMeterFile(MeterLutFile.StrLutMeterFileName, out meterLutFile.BinData);
|
||||
|
||||
// Separate to maximum line length of 16 bytes
|
||||
// Extract information from read meter LUT file
|
||||
var lutLineList = new List<String>();
|
||||
if (retVal)
|
||||
{
|
||||
for (var idx = 0; idx < meterLutFile.Count; idx += 16)
|
||||
// Validate the meter LUT file format
|
||||
var lutFileFormatValid = meterLutFile.ValidateLutFormat();
|
||||
var lutLine = $@"LUT Version: {meterLutFile.Version}";
|
||||
lutLineList.Add(lutLine);
|
||||
lutLine = $@"LUT {Resources.StrMessageMeterSize} " +
|
||||
$@"{MeterSizeConverter.ConvertMeterSizeEnumToSizeName(meterLutFile.MeterSize)}";
|
||||
lutLineList.Add(lutLine);
|
||||
lutLine = $@"{Resources.StrMessageLutCrc} 0x{meterLutFile.FileCrc:X4}";
|
||||
lutLineList.Add(lutLine);
|
||||
if (lutFileFormatValid)
|
||||
{
|
||||
// limit the length at the end to the remaining bytes
|
||||
var length = idx + 16 > meterLutFile.Count ? meterLutFile.Count - idx : 16;
|
||||
var lutLine = BitConverter.ToString(meterLutFile.GetRange(idx, length).ToArray());
|
||||
lutLineList.Add(lutLine);
|
||||
}
|
||||
}
|
||||
if (_fwUpdateSafeLutFile == null || _fwUpdateSafeLutFile.BinData.Count != MeterLutFile.SizeLutFile)
|
||||
{
|
||||
LogStringList(Resources.StrMessageLutFile, lutLineList,
|
||||
Resources.StrLutFileFromMeterValid);
|
||||
}
|
||||
else
|
||||
{
|
||||
for (var c = 0; c < MeterLutFile.SizeLutFile; c++)
|
||||
{
|
||||
// If one byte is different the comparison failed
|
||||
if (_fwUpdateSafeLutFile.BinData[c] != meterLutFile.BinData[c])
|
||||
{
|
||||
LogStringList(Resources.StrMessageLutFile, lutLineList,
|
||||
errorMessage: Resources.StrLutFileCompareFailed);
|
||||
retVal = false;
|
||||
}
|
||||
}
|
||||
|
||||
// Analyze the read out of LUT file
|
||||
if (meterLutFile == null || meterLutFile.Count == 0)
|
||||
{
|
||||
// Log information about LUT file is not installed
|
||||
if (_fwUpdateSafeLutFile == null)
|
||||
{
|
||||
LogText(Resources.StrLutFileNotNeeded);
|
||||
return true;
|
||||
}
|
||||
|
||||
// Here the LUT file should be installed but is not
|
||||
InfoProcessFailed(null, Resources.StrLutFileNotInstalled);
|
||||
retVal = false;
|
||||
}
|
||||
|
||||
// If the FW-Update safe does not contain a LUT file this cannot be compared
|
||||
if (_fwUpdateSafeLutFile == null)
|
||||
{
|
||||
// If the FW-Update safe does not contain a LUT file just log the read out
|
||||
if (lutLineList.Count != MeterLutFile.SizeLutFile )
|
||||
{
|
||||
LogStringList(Resources.StrMessageHashedPwdFile, lutLineList,
|
||||
errorMessage: Resources.StrLutFileNotDelivered);
|
||||
// Here all bytes are identical
|
||||
if (!retVal)
|
||||
{
|
||||
LogStringList(Resources.StrMessageLutFile, lutLineList,
|
||||
Resources.StrLutFileCompareSucceeded);
|
||||
}
|
||||
}
|
||||
}
|
||||
// Here the LUT file format is invalid
|
||||
else
|
||||
{
|
||||
LogErrorText(Resources.StrLutFileNotDelivered);
|
||||
}
|
||||
}
|
||||
else if (!_passwordFileIsCorrupted)
|
||||
{
|
||||
// Compare the installed LUT file with the LUT file from FW update safe
|
||||
retVal = !meterFile.VerifyMeterFile(MeterLutFile.StrLutMeterFileName,
|
||||
_fwUpdateSafeLutFile.BinData.ToArray());
|
||||
|
||||
if (!retVal)
|
||||
{
|
||||
LogStringList(Resources.StrMessageLutFile, lutLineList,
|
||||
Resources.StrLutFileCompareSucceeded);
|
||||
}
|
||||
else
|
||||
{
|
||||
// LUT file is suspicious
|
||||
LogStringList(Resources.StrMessageLutFile, lutLineList,
|
||||
errorMessage: Resources.StrLutFileCompareFailed);
|
||||
errorMessage: Resources.StrLutFileFromMeterInvalid);
|
||||
retVal = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -3958,23 +3948,25 @@ namespace Xylem.ServiceFwUpdate.Ui.ServiceFwUpdateSw
|
||||
/// </summary>
|
||||
/// <param name="successExitState"></param>
|
||||
/// <param name="errorExitState"></param>
|
||||
/// <remarks date="2023-Nov-09" author="Thomas Wiedebusch">
|
||||
/// <remarks date="2023-Nov-13" author="Thomas Wiedebusch">
|
||||
/// - Initial.
|
||||
/// </remarks>
|
||||
private void RestoreLutFile(ProcessState successExitState, ProcessState errorExitState = ProcessState.Error)
|
||||
{
|
||||
// Remind the invoker being able to generate error messages based on the last state
|
||||
_invokerProcessState = _processState;
|
||||
InfoProcessActive(lblLutFileCheck, Resources.StrLutFileRestoreActive);
|
||||
|
||||
|
||||
//TODO THW implement the installation of the LUT
|
||||
// If meter LUT CRC is not set and the meter files do not report the LUT, the meter does not have an
|
||||
// installed LUT
|
||||
// 1. LUT file NOT installed:
|
||||
// If meter LUT CRC is not set and the meter files do not report the LUT, the meter does not have an
|
||||
// installed LUT
|
||||
if ((string.IsNullOrEmpty(_currentGenesis.LutCrc) ||
|
||||
_currentGenesis.LutCrc.Equals(Constants.StrUnknown)) &&
|
||||
_currentGenesis.LutCrc.Equals(Constants.StrUnknown)) &&
|
||||
_readMeterFiles != null && !_readMeterFiles.Any(f => f.Contains(MeterLutFile.StrLutMeterFileName)))
|
||||
{
|
||||
// if the safe contains a LUT file, the installation of it has failed or it got lost during update
|
||||
// 1. a) LUT file not installed but required by the FW update safe:
|
||||
// If the safe contains a LUT file, the installation of it has failed or it got lost during
|
||||
// update
|
||||
if (_fwUpdateSafeLutFile != null)
|
||||
{
|
||||
LogErrorText(Resources.StrLutFileNotInstalled);
|
||||
@@ -3982,15 +3974,29 @@ namespace Xylem.ServiceFwUpdate.Ui.ServiceFwUpdateSw
|
||||
return;
|
||||
}
|
||||
|
||||
// this FW version does not require a LUT file
|
||||
// 1. b) LUT file not installed and not delivered by the FW update safe
|
||||
// This FW version does not require a LUT file
|
||||
LogText(Resources.StrLutFileNotNeeded);
|
||||
_processState = successExitState;
|
||||
return;
|
||||
}
|
||||
|
||||
// if the LUT is not in the safe it cannot be restored but can be logged
|
||||
ReadLogAndCompareMeterLutFile();
|
||||
_processState = errorExitState;
|
||||
// 2. LUT file is installed:
|
||||
// 2.a) Lut file is installed but NOT in the safe:
|
||||
// If the LUT is not in the safe it cannot be restored or compared to the required content but can
|
||||
// be analyzed and logged
|
||||
// 2.b) LUT file is installed and delivered by the FW update safe:
|
||||
// On validated installed LUT file in meter this can be compared with the required LUT file
|
||||
if (!ReadLogAndCompareMeterLutFile())
|
||||
{
|
||||
InfoProcessFailed(lblLutFileCheck, Resources.StrLutFileFromMeterInvalid);
|
||||
_processState = errorExitState;
|
||||
}
|
||||
else
|
||||
{
|
||||
InfoProcessSuccess(lblLutFileCheck, Resources.StrLutFileFromMeterValid);
|
||||
_processState = successExitState;
|
||||
}
|
||||
|
||||
// Change first the process state, otherwise the timer may switch the bar on again
|
||||
SetOverallProgressDisplayOff();
|
||||
|
||||
@@ -601,6 +601,24 @@ namespace Xylem.ServiceFwUpdate.Ui.ServiceFwUpdateSw.Properties {
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Looks up a localized string similar to ERROR: LUT installed in meter is invalid!.
|
||||
/// </summary>
|
||||
internal static string StrLutFileFromMeterInvalid {
|
||||
get {
|
||||
return ResourceManager.GetString("StrLutFileFromMeterInvalid", resourceCulture);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Looks up a localized string similar to LUT installed in meter is valid..
|
||||
/// </summary>
|
||||
internal static string StrLutFileFromMeterValid {
|
||||
get {
|
||||
return ResourceManager.GetString("StrLutFileFromMeterValid", resourceCulture);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Looks up a localized string similar to ERROR: LUT from FW update safe invalid!.
|
||||
/// </summary>
|
||||
@@ -610,6 +628,15 @@ namespace Xylem.ServiceFwUpdate.Ui.ServiceFwUpdateSw.Properties {
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Looks up a localized string similar to LUT from FW update safe is valid..
|
||||
/// </summary>
|
||||
internal static string StrLutFileFromSafeValid {
|
||||
get {
|
||||
return ResourceManager.GetString("StrLutFileFromSafeValid", resourceCulture);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Looks up a localized string similar to ERROR: LUT is not in FW updae safe!.
|
||||
/// </summary>
|
||||
@@ -700,15 +727,6 @@ namespace Xylem.ServiceFwUpdate.Ui.ServiceFwUpdateSw.Properties {
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Looks up a localized string similar to LUT successfully validated..
|
||||
/// </summary>
|
||||
internal static string StrLutFileValid {
|
||||
get {
|
||||
return ResourceManager.GetString("StrLutFileValid", resourceCulture);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Looks up a localized string similar to Not installed.
|
||||
/// </summary>
|
||||
|
||||
@@ -646,10 +646,16 @@
|
||||
<data name="StrLutFileRestoreUnspecified" xml:space="preserve">
|
||||
<value>LUT wiederherstellen.</value>
|
||||
</data>
|
||||
<data name="StrLutFileValid" xml:space="preserve">
|
||||
<value>LUT ist gültig.</value>
|
||||
<data name="StrLutFileFromMeterValid" xml:space="preserve">
|
||||
<value>LUT installiert im Meter is gültig.</value>
|
||||
</data>
|
||||
<data name="StrMessageLutFile" xml:space="preserve">
|
||||
<value>LUT:</value>
|
||||
</data>
|
||||
<data name="StrLutFileFromMeterInvalid" xml:space="preserve">
|
||||
<value>FEHLER:LUT installiert im Meter ist ungültig!</value>
|
||||
</data>
|
||||
<data name="StrLutFileFromSafeValid" xml:space="preserve">
|
||||
<value>LUT im FW Update Safe ist gültig.</value>
|
||||
</data>
|
||||
</root>
|
||||
@@ -613,8 +613,8 @@
|
||||
<data name="StrLutFileNotNeeded" xml:space="preserve">
|
||||
<value>LUT not required for this FW.</value>
|
||||
</data>
|
||||
<data name="StrLutFileValid" xml:space="preserve">
|
||||
<value>LUT successfully validated.</value>
|
||||
<data name="StrLutFileFromMeterValid" xml:space="preserve">
|
||||
<value>LUT installed in meter is valid.</value>
|
||||
</data>
|
||||
<data name="StrLutFileCompareFailed" xml:space="preserve">
|
||||
<value>ERROR: Installed LUT is unequal to required!</value>
|
||||
@@ -652,4 +652,10 @@
|
||||
<data name="StrMessageLutFile" xml:space="preserve">
|
||||
<value>LUT:</value>
|
||||
</data>
|
||||
<data name="StrLutFileFromMeterInvalid" xml:space="preserve">
|
||||
<value>ERROR: LUT installed in meter is invalid!</value>
|
||||
</data>
|
||||
<data name="StrLutFileFromSafeValid" xml:space="preserve">
|
||||
<value>LUT from FW update safe is valid.</value>
|
||||
</data>
|
||||
</root>
|
||||
Reference in New Issue
Block a user