175 lines
11 KiB
Markdown
175 lines
11 KiB
Markdown
|
|
---
|
||
|
|
source_files:
|
||
|
|
- Common/DTS.Common.Serialization/TDAS/TDAS.File.Reader.BadCrcException.cs
|
||
|
|
- Common/DTS.Common.Serialization/TDAS/TDAS.File.Reader.MissingFileException.cs
|
||
|
|
- Common/DTS.Common.Serialization/TDAS/TDAS.File.Reader.TooManyFilesException.cs
|
||
|
|
- Common/DTS.Common.Serialization/TDAS/TDAS.File.IChannelHeader.cs
|
||
|
|
- Common/DTS.Common.Serialization/TDAS/TDAS.File.PersistentChannel.NotInitializedException.cs
|
||
|
|
- Common/DTS.Common.Serialization/TDAS/TDAS.File.PersistentChannel.DataTooBigForArrayException.cs
|
||
|
|
- Common/DTS.Common.Serialization/TDAS/TDAS.File.cs
|
||
|
|
- Common/DTS.Common.Serialization/TDAS/TDAS.File.BinaryChannelHeader.cs
|
||
|
|
- Common/DTS.Common.Serialization/TDAS/TDAS.File.Writer.cs
|
||
|
|
- Common/DTS.Common.Serialization/TDAS/TLFBin.cs
|
||
|
|
generated_at: "2026-04-16T03:38:54.525487+00:00"
|
||
|
|
model: "Qwen/Qwen3-Coder-Next-FP8"
|
||
|
|
schema_version: 1
|
||
|
|
sha256: "8202fee238e4de73"
|
||
|
|
---
|
||
|
|
|
||
|
|
# TDAS Serialization Module Documentation
|
||
|
|
|
||
|
|
## 1. Purpose
|
||
|
|
|
||
|
|
This module provides serialization and deserialization support for TDAS (Test Data Acquisition System) files, specifically handling `.tlf` (text-based metadata) and `.BIN` (binary channel data) file formats used by Diversified Technical Systems, Inc. It defines core types—including `File`, `Writer`, `Reader`, `PersistentChannel`, and supporting classes like `TDASBinaryChannelHeader`—to manage test metadata, channel headers, and raw data. The module enables structured export/import of test data with support for channel-specific metadata (e.g., acquisition rate, calibration levels, signal-to-noise ratio), CRC validation, and exception handling for common file-level and data-level errors.
|
||
|
|
|
||
|
|
## 2. Public Interface
|
||
|
|
|
||
|
|
### Exception Types
|
||
|
|
|
||
|
|
All exception types are nested within `File` or `File.PersistentChannel` and extend `Exception` or `ApplicationException`. Each provides three constructors: parameterless, `string msg`, and `string msg, Exception innerEx`.
|
||
|
|
|
||
|
|
- **`File.Reader.BadCrcException`**
|
||
|
|
Thrown when a CRC validation failure occurs during file reading (e.g., corrupted binary channel data or header).
|
||
|
|
|
||
|
|
- **`File.Reader.MissingFileException`**
|
||
|
|
Thrown when an expected file (e.g., `.tlf` or `.BIN`) is not found during deserialization.
|
||
|
|
|
||
|
|
- **`File.Reader.TooManyFilesException`**
|
||
|
|
Thrown when the number of channel files exceeds an internal limit during deserialization.
|
||
|
|
|
||
|
|
- **`File.PersistentChannel.NotInitializedException`**
|
||
|
|
Thrown when attempting to access a property of `PersistentChannel` that has not yet been initialized (e.g., reading `Data` before it's loaded).
|
||
|
|
|
||
|
|
- **`File.PersistentChannel.DataTooBigForArrayException`**
|
||
|
|
Thrown when attempting to materialize a large dataset into an array that exceeds safe memory constraints.
|
||
|
|
|
||
|
|
### Core Types
|
||
|
|
|
||
|
|
- **`File`**
|
||
|
|
Main entry point for TDAS file operations. Extends `Serialization.File` and implements `IWritable<Test>`.
|
||
|
|
- **`static string Extension => ".tlf"`**
|
||
|
|
The file extension for the primary metadata file.
|
||
|
|
- **`static string TestFileExtension => ".tlf"`**
|
||
|
|
Alias for `Extension`; used for test metadata files.
|
||
|
|
- **`static string ChannelFileExtension => ".BIN"`**
|
||
|
|
File extension for binary channel data files.
|
||
|
|
- **`static string CalculatedChannelFileExtension => ".cchn"`**
|
||
|
|
File extension for calculated channel files.
|
||
|
|
- **`IWriter<Test> Exporter`**
|
||
|
|
Lazily-initialized writer instance for serializing `Test` objects.
|
||
|
|
- **`IReader<Test> Importer`**
|
||
|
|
Lazily-initialized reader instance for deserializing `Test` objects.
|
||
|
|
- **`int GetChannelNumberFromChannelFileName(string channelFileName)`**
|
||
|
|
Extracts the 3-digit channel number from a channel filename (e.g., `"test.tlf001.BIN"` → `1`). Throws if parsing fails.
|
||
|
|
|
||
|
|
- **`File.TDASBinaryChannelHeader`**
|
||
|
|
Implements `IChannelHeader` and encapsulates binary channel header fields. Used to serialize/deserialize header metadata and compute CRCs.
|
||
|
|
- **Properties (get/set):**
|
||
|
|
`AcquisitionRate`, `NumberOfPreT0DataPoints`, `NumberOfPostT0DataPoints`,
|
||
|
|
`PreZeroLevelInCnts`, `PreCalLevelInCnts`, `SignalToNoiseRatioInDb`,
|
||
|
|
`PostZeroLevelInCnts`, `PostCalLevelInCnts`, `DataZeroLevelInCnts`,
|
||
|
|
`ScaleFactorMVPerCnt`, `ScaleFactorEUPerCnt`.
|
||
|
|
- **`UInt32 Crc32 { get; }`**
|
||
|
|
Computes CRC32 over all header fields (no EU string padding stripping).
|
||
|
|
- **`UInt32 UnpaddedEuCrc32 { get; }`**
|
||
|
|
Computes CRC32 with EU string padding stripped.
|
||
|
|
- **`UInt32 UnpaddedEuStringPaddedEuLengthCrc32 { get; }`**
|
||
|
|
Computes CRC32 with EU string stripped but EU length field included.
|
||
|
|
- **`private UInt32 CalculateCrc32(bool stripEuPadding, bool bKeepEuLength)`**
|
||
|
|
Internal CRC calculation using `Utils.Math_DoCRC16Step` on 16-bit word pairs of header data.
|
||
|
|
|
||
|
|
- **`File.Writer`**
|
||
|
|
Internal class implementing `IWriter<Test>` for writing `Test` objects to disk.
|
||
|
|
- **`void Write(string pathname, string id, string dataFolder, Test test, ...)`**
|
||
|
|
Writes a `Test` to disk:
|
||
|
|
- Serializes metadata to `<pathname>.tlf` using `TLF` class.
|
||
|
|
- Creates backup copy of `.tlf` file.
|
||
|
|
- Writes binary channel data to `<pathname>.NNN.BIN` files (`.BIN` extension), where `NNN` is a 3-digit channel number.
|
||
|
|
- Supports event callbacks (`beginEventHandler`, `tickEventHandler`, `errorEventHandler`, etc.).
|
||
|
|
- Throws `NotSupportedException` for the 5-parameter overload.
|
||
|
|
- **`void Initialize(...)`**
|
||
|
|
Currently a no-op stub.
|
||
|
|
|
||
|
|
- **`IChannelHeader`**
|
||
|
|
Interface defining contract for channel header metadata (implemented by `TDASBinaryChannelHeader`).
|
||
|
|
All properties are get/set; see `TDASBinaryChannelHeader` for descriptions.
|
||
|
|
|
||
|
|
- **`TLFBin`**
|
||
|
|
Helper class for serializing binary channel data with resampling and scaling.
|
||
|
|
- **Properties (get/set):**
|
||
|
|
`AcquisitionRate`, `PreTriggerDataPoints`, `PostTriggerDataPoints`,
|
||
|
|
`PreZeroLevel`, `PreCalLevel`, `SignalToNoiseRatio`,
|
||
|
|
`PostZeroLevel`, `PostCalLevel`, `SuperSampleRate`.
|
||
|
|
- **`TLFBin(Test.Module.Channel channel, double superSampleRate)`**
|
||
|
|
Constructor computes header fields and scaling parameters from `channel` and `superSampleRate`.
|
||
|
|
- `PreCalLevel` is hardcoded to `0.7 * short.MaxValue` (10922).
|
||
|
|
- `SignalToNoiseRatio` computed from `NoiseAsPercentageOfFullScale` and full-scale ADC range.
|
||
|
|
- `PostZeroLevel` and `PostCalLevel` are currently unimplemented (set to `0`).
|
||
|
|
- **`void Serialize(BinaryWriter bw, Test.Module.Channel channel)`**
|
||
|
|
Writes binary data to `BinaryWriter`:
|
||
|
|
- Writes header (11 fields: `SuperSampleRate`, `PreTriggerDataPoints`, ..., `ScaleFactorEUPerCnt`).
|
||
|
|
- Writes resampled ADC values (16-bit signed) for each sample, with interpolation.
|
||
|
|
- For digital inputs (`Bridge == DigitalInput`), writes 16-bit digital values based on `DigitalMode` and `DigitalMultiplier`.
|
||
|
|
- For linearized sensors, constrains `newADC` to `short.MinValue`/`short.MaxValue` to avoid underflow.
|
||
|
|
|
||
|
|
## 3. Invariants
|
||
|
|
|
||
|
|
- **File Naming Convention:**
|
||
|
|
Channel binary files follow `<base>.NNN.BIN`, where `NNN` is a 3-digit channel number (e.g., `001`, `002`, `901` for squib channels). Channel numbers are extracted via `GetChannelNumberFromChannelFileName`, which assumes the last 3 characters before `.BIN` are digits.
|
||
|
|
|
||
|
|
- **CRC Computation:**
|
||
|
|
CRC32 is computed over 16-bit words (little-endian) of header data. Padding is added if data length is odd. Uses `Utils.Math_DoCRC16Step` (not standard CRC32), and the result is returned as `UInt32`.
|
||
|
|
|
||
|
|
- **Data Resampling:**
|
||
|
|
`TLFBin.Serialize` resamples data to `SuperSampleRate` using linear interpolation. The resampling factor `rate = ceil(SuperSampleRate / AcquisitionRate)` is applied per sample.
|
||
|
|
|
||
|
|
- **Digital Input Handling:**
|
||
|
|
Digital channels output 16-bit values based on `DigitalMode` (e.g., `CCNC`, `TLH`) and thresholds (`breakPoint`). Values are determined per interpolated step.
|
||
|
|
|
||
|
|
- **Linearization Constraints:**
|
||
|
|
For linearized sensors, `newADC` is clamped to `short.MinValue`/`short.MaxValue` to prevent overflow/underflow during serialization (see `TLFBin.Serialize`).
|
||
|
|
|
||
|
|
## 4. Dependencies
|
||
|
|
|
||
|
|
- **Internal Dependencies:**
|
||
|
|
- `DTS.Common.Utilities.DotNetProgrammingConstructs.Property<T>` (used in `File` for static extension properties).
|
||
|
|
- `DTS.Common.Utilities.Logging.APILogger` (used in `File.Writer.Write` for error logging).
|
||
|
|
- `DTS.Common.Constant` and `DTS.Common.Enums.Sensors.SensorConstants` (used in `TLFBin` constructor for `BridgeType.DigitalInput`).
|
||
|
|
- `DTS.Common.Enums.DigitalInputModes` (used in `TLFBin.Serialize` for digital input mode handling).
|
||
|
|
- `SliceRaw.File.Reader.GetDataScaler` (used in `TLFBin.Serialize` to obtain scaling parameters).
|
||
|
|
- `Utils.Math_DoCRC16Step` (used in `TDASBinaryChannelHeader.CalculateCrc32`).
|
||
|
|
- `Serialization.File`, `IWriter<Test>`, `IReader<Test>` (base types for `File`, `Writer`, and `Reader`).
|
||
|
|
|
||
|
|
- **External Dependencies:**
|
||
|
|
- `System`, `System.IO`, `System.Linq`, `System.Text`, `System.Collections.Generic` (standard .NET libraries).
|
||
|
|
- `DTS.Serialization.Test` and its nested types (`Test.Module.Channel`, `Test.Module.AnalogInputChannel`, `Test.Module.Channel.PersistentChannelInfo`).
|
||
|
|
- `FilteredData`, `BeginEventHandler`, `CancelEventHandler`, etc. (event delegates for progress/error callbacks).
|
||
|
|
|
||
|
|
## 5. Gotchas
|
||
|
|
|
||
|
|
- **`TDASBinaryChannelHeader.CalculateCrc32` uses CRC16, not CRC32:**
|
||
|
|
Despite the property names (`Crc32`, `UnpaddedEuCrc32`, etc.), the implementation computes a 16-bit CRC using `Math_DoCRC16Step` and returns it as `UInt32`. This is likely a historical naming inconsistency.
|
||
|
|
|
||
|
|
- **`PreCalLevel` is hardcoded:**
|
||
|
|
In `TLFBin` constructor, `PreCalLevel` is set to `0.7 * short.MaxValue` (10922) instead of a configurable value. The comment suggests this is a placeholder.
|
||
|
|
|
||
|
|
- **`PostZeroLevel` and `PostCalLevel` are unimplemented:**
|
||
|
|
Both are set to `0` in `TLFBin` constructor with `@TODO` comments indicating missing data sources.
|
||
|
|
|
||
|
|
- **Digital input `breakPoint` logic is complex and mode-dependent:**
|
||
|
|
Thresholds differ by `DigitalMode` (e.g., `CCNC` vs `TLH`) and input type (current vs voltage). Misconfiguration may lead to incorrect digital output values.
|
||
|
|
|
||
|
|
- **`TLFBin.Serialize` may produce out-of-range values for linearized sensors:**
|
||
|
|
Although `newADC` is clamped to `short.MinValue`/`short.MaxValue`, the comment notes this was added to fix underflow in bug #14496. Ensure scaling factors and sensor capacities are valid to avoid unexpected clamping.
|
||
|
|
|
||
|
|
- **Channel number extraction is fragile:**
|
||
|
|
`GetChannelNumberFromChannelFileName` assumes filenames end with `.BIN` or `.bin` and that the 3 characters before the extension are digits. Filenames like `_C001.BIN` are handled, but edge cases (e.g., `.BIN` in middle of name) may cause errors.
|
||
|
|
|
||
|
|
- **`File.Writer.Write` has two overloads, only one implemented:**
|
||
|
|
The 5-parameter overload throws `NotSupportedException`. Ensure callers use the 15-parameter version.
|
||
|
|
|
||
|
|
- **No public `Reader` class defined in source:**
|
||
|
|
While `File.Importer` returns `IReader<Test>`, the `Reader` class is not defined in the provided files. Its implementation is likely in `TDAS.File.Reader.cs` (referenced in comments but not included).
|
||
|
|
|
||
|
|
- **Encoding assumptions:**
|
||
|
|
`File.Writer.Write` uses `Encoding.Default` for `.tlf` serialization. This may cause portability issues across systems with different default encodings.
|