227 lines
9.3 KiB
Plaintext
227 lines
9.3 KiB
Plaintext
|
|
using DTS.Common.Constant.DASSpecific;
|
||
|
|
using DTS.Common.Enums.DASFactory;
|
||
|
|
using DTS.Common.Enums.Sensors;
|
||
|
|
using DTS.Common.ICommunication;
|
||
|
|
using DTS.Common.Interface.Connection;
|
||
|
|
using DTS.Common.Interface.DASFactory.Config;
|
||
|
|
using DTS.Common.Utilities.Logging;
|
||
|
|
using DTS.DASLib.Command.SLICE;
|
||
|
|
using System;
|
||
|
|
using System.Collections.Generic;
|
||
|
|
using System.Linq;
|
||
|
|
|
||
|
|
namespace DTS.DASLib.Service
|
||
|
|
{
|
||
|
|
#pragma warning disable S101 // Types should be named in PascalCase
|
||
|
|
public class SLICE6AIRTC<T> : SLICE6_Base<T>, IAlignUDPToPPSAware where T : IConnection, new()
|
||
|
|
#pragma warning restore S101 // Types should be named in PascalCase
|
||
|
|
{
|
||
|
|
public bool AlignUDPToPPS { get; set; }
|
||
|
|
public override bool SupportsRemoveLeapSeconds => true;
|
||
|
|
public override bool SupportsADCSamplesPerPacket => true;
|
||
|
|
protected override bool RequiresNon0QualificationSamples => true;
|
||
|
|
protected override byte[] GetRTChannelIndices(RealTimeAsyncPacket packet)
|
||
|
|
{
|
||
|
|
return new byte[] { 0x00, 0x01, 0x02, 0x03, 0x04, 0x05 };
|
||
|
|
}
|
||
|
|
public override void SetIsStreamingSupported(bool supported = false)
|
||
|
|
{
|
||
|
|
IsStreamingSupported = true;
|
||
|
|
}
|
||
|
|
///// <summary>
|
||
|
|
///// the order of this DAS among multiple das
|
||
|
|
///// </summary>
|
||
|
|
//public int DASIndex { get; set; } = -1;
|
||
|
|
|
||
|
|
public override void InitMinProto()
|
||
|
|
{
|
||
|
|
// SLICE 6.0 Protocol Limitations
|
||
|
|
SLICE6AIR_TC_MinimumProtocols[DFConstantsAndEnums.ProtocolLimitedCommands.ADCSamplesPerPacket] = SLICE6AIRTC.ADC_SAMPLES_PER_PACKET_VER;
|
||
|
|
MinimumProtocols = SLICE6AIR_TC_MinimumProtocols;
|
||
|
|
}
|
||
|
|
|
||
|
|
#region protocol settings/overrides
|
||
|
|
private readonly Dictionary<DFConstantsAndEnums.ProtocolLimitedCommands, byte> SLICE6AIR_TC_MinimumProtocols =
|
||
|
|
new Dictionary<DFConstantsAndEnums.ProtocolLimitedCommands, byte>();
|
||
|
|
|
||
|
|
protected override int MIN_PROTOCOL_TMATS_INTERVAL => SLICE6AIRBR.MIN_PROTOCOL_VER;
|
||
|
|
|
||
|
|
private uint maxSampleRateHz = 0;
|
||
|
|
protected override uint MaxSampleRateHz
|
||
|
|
{
|
||
|
|
get
|
||
|
|
{
|
||
|
|
if (0 == maxSampleRateHz)
|
||
|
|
{
|
||
|
|
try
|
||
|
|
{
|
||
|
|
var qsa = new QuerySystemAttributeSLICE6(this)
|
||
|
|
{
|
||
|
|
Key = AttributeTypes.SystemAttributesSLICE6.MaximumSampleRate
|
||
|
|
};
|
||
|
|
qsa.SyncExecute();
|
||
|
|
maxSampleRateHz = (uint)qsa.Value;
|
||
|
|
}
|
||
|
|
catch (Exception ex)
|
||
|
|
{
|
||
|
|
APILogger.Log("Error getting S6A-BR max sample rate, returning 50K");
|
||
|
|
APILogger.LogException(ex);
|
||
|
|
return 50000;
|
||
|
|
}
|
||
|
|
}
|
||
|
|
return maxSampleRateHz;
|
||
|
|
}
|
||
|
|
}
|
||
|
|
#endregion
|
||
|
|
|
||
|
|
protected override DASModule MakeConfigModuleFromInfoModule(InfoResult.Module infoModule)
|
||
|
|
{
|
||
|
|
//per LP: can stream, no IEPE
|
||
|
|
var configModule = new DASModule(infoModule.ModuleArrayIndex, this);
|
||
|
|
configModule.Channels = new DASChannel[infoModule.NumberOfChannels];
|
||
|
|
|
||
|
|
for (var i = 0; i < infoModule.NumberOfChannels; i++)
|
||
|
|
{
|
||
|
|
if (DFConstantsAndEnums.ModuleType.StreamOut == configModule.ModuleType())
|
||
|
|
{
|
||
|
|
var streamOutChannel = new StreamOutputDASChannel(configModule, i);
|
||
|
|
configModule.Channels[i] = streamOutChannel;
|
||
|
|
}
|
||
|
|
else
|
||
|
|
{
|
||
|
|
var channel = new AnalogInputDASChannel(configModule, i);
|
||
|
|
|
||
|
|
channel.SupportedBridges = new SensorConstants.BridgeType[]
|
||
|
|
{
|
||
|
|
SensorConstants.BridgeType.FullBridge,
|
||
|
|
SensorConstants.BridgeType.HalfBridge,
|
||
|
|
};
|
||
|
|
configModule.Channels[i] = channel;
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
return configModule;
|
||
|
|
}
|
||
|
|
|
||
|
|
/// <summary>
|
||
|
|
/// we can probably simplify and take common items (slice6+slice1) out of this function, but for now
|
||
|
|
/// it's mostly a copy of SLICE1.AsyncConfigure
|
||
|
|
/// </summary>
|
||
|
|
/// <param name="configAsyncInfo"></param>
|
||
|
|
protected override void AsyncConfigure(object configAsyncInfo)
|
||
|
|
{
|
||
|
|
var info = configAsyncInfo as SliceConfigServiceAsyncInfo;
|
||
|
|
SetUDPAlignOnPPS();
|
||
|
|
SetRemoveSeconds();
|
||
|
|
SetADCSamplesPerPacket(info.StreamADCPerPacket[this]);
|
||
|
|
|
||
|
|
//12638 DAS does not record data in recorder mode during calibration ~ 40% of time.
|
||
|
|
//for SLICE6 we call reseteventlist here, prior to configuring and NOT before arming
|
||
|
|
ResetEventListPriorToConfigure();
|
||
|
|
|
||
|
|
int progressValue = 0;
|
||
|
|
bool bReleased = true;
|
||
|
|
|
||
|
|
if (IsCommandSupported(DFConstantsAndEnums.ProtocolLimitedCommands.ProgramStackChannels))
|
||
|
|
{
|
||
|
|
ReconfigureAccordingToConfig();
|
||
|
|
}
|
||
|
|
|
||
|
|
PresetSampleRate();
|
||
|
|
|
||
|
|
SetVoltageRequirements();
|
||
|
|
|
||
|
|
SetPolarity();
|
||
|
|
|
||
|
|
SetArmDisableShortCheck();
|
||
|
|
|
||
|
|
try
|
||
|
|
{
|
||
|
|
Lock();
|
||
|
|
bReleased = false;
|
||
|
|
// loop thru the modules (slices) and configure the non-UART channels
|
||
|
|
var numChannels = DASInfo.Modules.Sum(mod => mod.NumberOfChannels);
|
||
|
|
var numStreamingChannels = DASInfo.Modules.Sum(mod => DFConstantsAndEnums.ModuleType.StreamOut == mod.TypeOfModule ? mod.NumberOfChannels : 0);
|
||
|
|
var rangeArray = new float[numChannels];
|
||
|
|
//var IsHalfBridgeArray = new bool[numChannels];
|
||
|
|
var bridgeModeArray = new byte[numChannels];
|
||
|
|
var BridgeResistanceArray = new ushort[numChannels];
|
||
|
|
var IsACCoupledArray = new bool[numChannels];
|
||
|
|
//18294 Implement Bridge AC / DC coupling(fw update dependent)
|
||
|
|
var bridgeACCouplingArray = new bool[numChannels];
|
||
|
|
// level trigger values
|
||
|
|
var enableLowerLevelTriggerThreshold = new bool[numChannels];
|
||
|
|
var enableUpperLevelTriggerThreshold = new bool[numChannels];
|
||
|
|
var lowerLevelTriggerThreshold = new float[numChannels];
|
||
|
|
var upperLevelTriggerThreshold = new float[numChannels];
|
||
|
|
var qualificationSamples = new int[numChannels];
|
||
|
|
|
||
|
|
var diagnosticChannels = new List<byte>();
|
||
|
|
|
||
|
|
var bModified = false;
|
||
|
|
CommonConfigureWork(diagnosticChannels, qualificationSamples, ref bReleased,
|
||
|
|
info, bridgeModeArray, IsACCoupledArray, BridgeResistanceArray,
|
||
|
|
ref bModified, rangeArray, enableUpperLevelTriggerThreshold, upperLevelTriggerThreshold,
|
||
|
|
enableLowerLevelTriggerThreshold, lowerLevelTriggerThreshold, bridgeACCouplingArray);
|
||
|
|
if (bReleased) { return; }
|
||
|
|
// report progress
|
||
|
|
progressValue = 5;
|
||
|
|
info.Progress(progressValue);
|
||
|
|
|
||
|
|
StoreConfigAttributes(info, rangeArray, ref bReleased, ref progressValue, bridgeModeArray,
|
||
|
|
IsACCoupledArray, BridgeResistanceArray, enableLowerLevelTriggerThreshold, lowerLevelTriggerThreshold,
|
||
|
|
enableUpperLevelTriggerThreshold, upperLevelTriggerThreshold, qualificationSamples, numChannels,
|
||
|
|
out var config, bridgeACCouplingArray, 0, numStreamingChannels);
|
||
|
|
|
||
|
|
progressValue = 20;
|
||
|
|
info.Progress(progressValue);
|
||
|
|
|
||
|
|
RemainingConfigWork(ref progressValue, info, diagnosticChannels, config, ref bReleased, null, null, null);
|
||
|
|
}
|
||
|
|
catch (CanceledException)
|
||
|
|
{
|
||
|
|
if (!bReleased)
|
||
|
|
{
|
||
|
|
bReleased = true;
|
||
|
|
Release();
|
||
|
|
}
|
||
|
|
|
||
|
|
info.Cancel();
|
||
|
|
}
|
||
|
|
catch (Exception ex)
|
||
|
|
{
|
||
|
|
if (!bReleased)
|
||
|
|
{
|
||
|
|
bReleased = true;
|
||
|
|
Release();
|
||
|
|
}
|
||
|
|
|
||
|
|
info.Error(ex.Message, ex);
|
||
|
|
}
|
||
|
|
finally
|
||
|
|
{
|
||
|
|
if (!bReleased)
|
||
|
|
{
|
||
|
|
bReleased = true;
|
||
|
|
Release();
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
info.Progress(100);
|
||
|
|
info.Success();
|
||
|
|
}
|
||
|
|
/// <summary>
|
||
|
|
/// returns true if the device is known to be streaming
|
||
|
|
/// does not query device, just returns a flag if it has been set
|
||
|
|
/// </summary>
|
||
|
|
public override bool GetIsStreaming()
|
||
|
|
{
|
||
|
|
if (null == DASArmStatus) { return false; }
|
||
|
|
//18852 Cannot use Stop streaming / (Dis)Auto Arm button if one or more DAS is idle
|
||
|
|
//can't rely on just having received invalid mode, QATS will still have a status of realtime
|
||
|
|
//when streaming, so we'll use either for now.
|
||
|
|
return DASArmStatus.ReceivedInvalidModeDuringSetup || DASArmStatus.IsInRealtime;
|
||
|
|
}
|
||
|
|
}
|
||
|
|
}
|