--- source_files: - Common/DTS.Common/Classes/DASFactory/DiagnosticMessageRow.cs - Common/DTS.Common/Classes/DASFactory/TCDiagnosticResult.cs - Common/DTS.Common/Classes/DASFactory/CanDiagnostics.cs - Common/DTS.Common/Classes/DASFactory/TemperatureConfig.cs - Common/DTS.Common/Classes/DASFactory/TMSNConfig.cs generated_at: "2026-04-16T03:17:33.495209+00:00" model: "Qwen/Qwen3-Coder-Next-FP8" schema_version: 1 sha256: "d29076d9515007bc" --- # Documentation: DASFactory Diagnostic & Configuration Classes ## 1. Purpose This module provides core data structures for representing and managing diagnostic results and configuration data within the DASFactory subsystem. It defines classes to encapsulate CAN bus diagnostics (`CanDiagnostics`), test channel diagnostics (`TCDiagnosticResult`), raw diagnostic message rows (`DiagnosticMessageRow`), and hardware-specific configuration objects for temperature logging (`TemperatureConfig`) and TMNS (Telemetry Network Subsystem) streaming (`TMNSConfig`). These classes serve as standardized data contracts between diagnostic test execution, result reporting, and configuration management layers—primarily supporting CAN BIST (Built-In Self-Test) and environmental monitoring, with extensibility for future hardware types. ## 2. Public Interface ### `DiagnosticMessageRow` - **`DiagnosticMessageRow(string field, string value, string verdict)`** Constructor initializing all three properties. Used to hold a single diagnostic message row (e.g., from CAN BIST output). - **`Field` (string, get/set)** Name of the diagnostic field (e.g., "ErrorCounter", "StatusRegister"). - **`Value` (string, get/set)** String representation of the diagnostic value. - **`Verdict` (string, get/set)** Pass/fail/other verdict for the field. - **`ToString()` (override)** Returns formatted string: `"Field: {Field}, Value: {Value}, Verdict: {Verdict}"`. ### `TCDiagnosticResult` - **`ChannelName` (string, get/set)** Human-readable name of the test channel. - **`ChannelIndex` (int, get/set)** Numeric index of the test channel. - **`CurrentReading` (double?, get/set)** Optional measured value (e.g., current in mA); `null` if not measured or unavailable. - **`Status` (DiagnosticStatus, get/set)** Overall diagnostic status (e.g., `Untested`, `Pass`, `Fail`). - **`ConnectionStatus` (ConnectionStatuses, get/set)** Connection state (e.g., `NotTested`, `Connected`, `Open`, `Short`). - **`Copy(ITCDiagnosticResult source)`** Copies all properties from `source` to this instance. ### `CanDiagnostics` - **`Active` (bool, get/set)** Whether this CAN channel is active. - **`ChannelIndex` (int, get/set)** CAN channel index (e.g., 0, 1). - **`Data` (int, get/set)** Raw data value from CAN diagnostics. - **`ErrorFrame` (int, get/set)** Count of error frames detected. - **`Load` (double, get/set)** Bus load percentage (0.0–100.0). - **`Overruns` (int, get/set)** Count of overrun errors. - **`LastUpdate` (DateTime, get/set)** Timestamp of last diagnostic update. - **`Errors` (int, read-only)** Computed error count: `Overruns` if `ErrorFrame == 0`, otherwise `1 + Overruns`. - **`ChannelName` (string, get/set)** Human-readable CAN channel name. - **`Copy(ICanDiagnosticResult source)`** Copies all properties from `source` to this instance. ### `TemperatureConfig` - **`LogEnable` (ushort, get/set)** Enable flag for logging (typically 0 or 1). - **`LogIntervalSec` (ushort, get/set)** Logging interval in seconds. - **`Channels` (ushort, get/set)** Bitfield representing enabled temperature/humidity channels (maps to `_channels` BitArray). - **`MCUTemp` (bool, get/set)** Enables/disables MCU temperature logging. - **`OnBoardHumidity` (bool, get/set)** Enables/disables on-board humidity logging. - **`EnvironmentalCh1`–`EnvironmentalCh4` (bool, get/set)** Enables/disables individual environmental channels (Ch1–Ch4). - **`ToUShortArray()` (ushort[])** Returns `[LogEnable, LogIntervalSec, Channels, Reserved]`. - **`TemperatureConfig(ushort[])`** Constructor initializing from a `ushort[]` (indices 0–2 used; index 3 ignored). - **`GetChannelsArray()` (int[])** Returns array of enabled channel indices (0–15) based on `_channels` BitArray. - **`GetMeasurementChannels()` (S6DBDiagnosticChannelList[])** Returns list of `S6DBDiagnosticChannelList` enum values corresponding to enabled channels. - **`GetChannelBitForDiagChannel(S6DBDiagnosticChannelList ch)` (TempLogChannelBits)** Maps a diagnostic channel enum to its corresponding `TempLogChannelBits` enum value; throws `NullReferenceException` if not found. ### `TMNSConfig` - **`TMNS_PCMSubFrameId` (uint, get/set)** PCM sub-frame ID. - **`TMNS_MsgId` (uint, get/set)** TMNS message ID. - **`TMNS_PCMMinorPerMajor` (uint, get/set)** PCM minor-per-major setting. - **`TMNS_TMATSPortNumber` (uint, get/set)** TMATs port number. - **`IENAUDP_PortNumber` (uint, get/set)** IENA UDP source port number. - **`TMNS5`, `TMNS6`, `TMNS7` (uint, get/set)** Reserved fields. - **`Fields` enum** Defines field indices: `TMNS_PCMSubFrameID`, `TMNS_MsgId`, `TMNS_PCMMinorPerMajor`, `TMNS_TMATSPortNumber`, `IENAUDP_PortNumber`, `TMNS5`, `TMNS6`, `TMNS7`. - **`TMNSConfig(uint[])`** Constructor from `uint[]` (length truncated to 8 if longer; shorter arrays padded with zeros). - **`TMNSConfig(string)`** Constructor from comma-separated string (e.g., `"(1,2,3)"`); parses to `uint[]`. - **`SetValue(Fields, uint)` / `GetValue(Fields)`** Set/get field value by enum. - **`ToUintArray()` (uint[])** Returns a copy of the internal `uint[]`. - **`ToCSVString()` (string)** Returns config as `(x,y,z,...)` string. - **`IsCh10(UDPStreamProfile)` (static bool)** Returns `true` if profile is a CH10 variant. - **`IsIENA(UDPStreamProfile)` (static bool)** Returns `true` if profile is `IENA_PTYPE_STREAM`. - **`IsTMNS(UDPStreamProfile)` (static bool)** Returns `true` if profile is `TMNS_PCM_STANDARD` or `TMNS_PCM_SUPERCOM`. - **`IsUART(UDPStreamProfile)` (static bool)** Returns `true` if profile is `UART_STREAM`. ## 3. Invariants - **`DiagnosticMessageRow`**: All three properties (`Field`, `Value`, `Verdict`) are non-null after construction (constructor assigns directly; no validation beyond constructor initialization). - **`TCDiagnosticResult`**: `ChannelIndex` defaults to `0`; `Status` defaults to `DiagnosticStatus.Untested`; `ConnectionStatus` defaults to `ConnectionStatuses.NotTested`; `CurrentReading` defaults to `null`. - **`CanDiagnostics`**: `ChannelIndex` defaults to `-1`; `Active` defaults to `false`; `Errors` is computed as `Overruns` if `ErrorFrame == 0`, else `1 + Overruns` (no negative values possible). - **`TemperatureConfig`**: - `_channels` BitArray is always 16 bits (initialized as `new BitArray(new[] { 0x00, 0x00 })`). - `Reserved` is a compile-time constant `0` and not stored in the config array. - `ToUShortArray()` always returns 4 elements: `[LogEnable, LogIntervalSec, Channels, 0]`. - `GetChannelBitForDiagChannel()` throws `NullReferenceException` for unmapped channels (no fallback). - **`TMNSConfig`**: - Internal `_values` array is always exactly 8 elements (size derived from `Fields` enum). - `ToUintArray()` returns a copy (not a reference). - `ToCSVString()` always includes parentheses and exactly 8 comma-separated values. ## 4. Dependencies ### This module depends on: - **`DTS.Common.Interface.DASFactory.Diagnostics`** (interfaces: `ITCDiagnosticResult`, `ICanDiagnosticResult`) - **`DTS.Common.Interface.Sensors.AnalogDiagnostics`** (used in `TCDiagnosticResult`) - **`DTS.Common.Enums.DASFactory`** (for `TempLogChannelBits`, `S6DBDiagnosticChannelList`, `DFConstantsAndEnums`) - **`DTS.Common.Enums`** (for `UDPStreamProfile` in `TMNSConfig`) - **`DTS.Common.Base`** (`BasePropertyChanged` base class for `TCDiagnosticResult` and `CanDiagnostics`) ### This module is depended upon by: - **Diagnostic test runners** (e.g., CAN BIST, temperature logging, TMNS configuration tools) that instantiate and populate these classes. - **UI/view layers** that bind to `TCDiagnosticResult`/`CanDiagnostics` via `INotifyPropertyChanged` (via `BasePropertyChanged`). - **Configuration serialization/deserialization** (e.g., saving/loading `TemperatureConfig` or `TMNSConfig` to/from storage). - **Diagnostic result aggregation** (e.g., combining `DiagnosticMessageRow` entries into test reports). ## 5. Gotchas - **`TemperatureConfig.GetChannelBitForDiagChannel()` throws `NullReferenceException`** for unmapped channels—despite the method name suggesting a safe lookup, it does not use `TryGetValue`. Callers must ensure the channel is supported. - **`TMNSConfig` string constructor is permissive**: Truncates or pads input to 8 fields; silently ignores non-parseable tokens (defaults to `0`). - **`TemperatureConfig.Channels` setter uses `BitConverter.ToUInt16`**: Assumes little-endian byte order (standard on .NET Core/.NET 5+ but platform-dependent in older frameworks). - **`CanDiagnostics.Errors` is computed, not stored**: Changes to `ErrorFrame` or `Overruns` trigger `OnPropertyChanged("Errors")`, but consumers must subscribe to `PropertyChanged` to react to this derived value. - **`DiagnosticMessageRow` stores everything as `string`**: No type safety or parsing; callers must handle numeric/string interpretation. - **`TMNSConfig` static methods (`IsCh10`, `IsIENA`, etc.) operate on `UDPStreamProfile` enum**: Behavior depends on complete enum coverage; missing cases in `switch` statements could cause incorrect results if new profiles are added. - **`TCDiagnosticResult` and `CanDiagnostics` implement `INotifyPropertyChanged` via `BasePropertyChanged`**: Property changes are observable, but `Copy()` does *not* raise `PropertyChanged` events for the copied values—consumers may need to manually trigger updates.