--- source_files: - DataPRO/EquipmentExchange/CrashDesignerTestSetup.cs generated_at: "2026-04-16T03:44:55.174600+00:00" model: "Qwen/Qwen3-Coder-Next-FP8" schema_version: 1 sha256: "75b4cd844b9f7d36" --- # EquipmentExchange ## Documentation: `CrashDesignerTestSetup` Module --- ### 1. Purpose This module defines the data model and XML deserialization logic for importing test setup configurations generated by *CrashDesigner* (a proprietary crash testing application). Its primary role is to parse an XML file conforming to a specific schema (with root ``) into a strongly-typed object graph (`CrashDesignerTestSetup`), enabling downstream components to access test metadata, channel groupings, and data acquisition (DAQ) hardware configuration in a structured manner. It also provides a utility method (`GetEqxElectricalMethod`) to map equipment bridge types to internal sensor configuration flags used elsewhere in the system. --- ### 2. Public Interface #### `CrashDesignerTestSetup` Class - **`string Name { get; set; }`** The name of the test setup, extracted from the `Name` attribute of the `` XML element. - **`static void GetEqxElectricalMethod(string eqxBridge, out bool isProportional, out DTS.Common.Enums.Sensors.SensorConstants.BridgeType bridgeType)`** Maps a string-based equipment bridge identifier (`eqxBridge`) to internal sensor configuration flags. - `isProportional`: `true` for passive bridges (e.g., `FullBridge`, `HalfBridge`, `QuarterBridge`), `false` for active sensors (e.g., `Active`, `ActiveSensor`, `HalfBridgeActive`, `QuarterBridgeActive`). - `bridgeType`: One of `DTS.Common.Enums.Sensors.SensorConstants.BridgeType` (`FullBridge`, `HalfBridge`, `QuarterBridge`, `IEPE`). - Special case: `"PiezoInput"` → `IEPE`, `isProportional = true`. - **`static CrashDesignerTestSetup ReadXML(string importFile)`** Loads and deserializes an XML file (`importFile`) into a `CrashDesignerTestSetup` instance. - Requires root element `` with `Name` attribute. - Delegates parsing of ``, ``, and `` sub-elements to respective `ReadXml` methods. - Logs unknown XML elements via `Trace.WriteLine`. #### Nested Classes & Methods - **`GeneralSection`** - **Properties**: `DateGenerated`, `GeneratorName`, `Description`, `TestType`, `PreTriggerTime`, `PostTriggerTime`, `OutputDataDirectory`, `TestSetupGroup` (string array). - **`void ReadXml(XmlElement root)`**: Parses child elements corresponding to `GeneralSection.Fields` enum values. - `PreTriggerTimeReadout` → `PreTriggerTime` - `PostTriggerTimeReadout` → `PostTriggerTime` - `TestSetupGroup` → appends to internal list (multiple allowed). - Uses invariant culture for numeric/date parsing; logs failures. - **`ChannelGroupsSection`** - **`Group[] Groups { get; }`**: Array of `Group` objects. - **`void ReadXml(XmlElement root)`**: Parses `` child elements. - **`Group`** - **Properties**: `Name`, `Id`, `Parent`, `Description`. - **`bool HasProperty(string key)` / `string GetProperty(string key)` / `void SetProperty(string key, string value)`**: Key-value store for arbitrary properties. - **`KnownFormats` enum**: Lists 30+ standardized property keys (e.g., `ISOTitle`, `TestDate`, `CustomerName`, `Velocity`, `Mass`, `ImpactSide`) with `[Description]` attributes matching their XML element names. - **`static Group ReadXml(XmlElement root)`**: Parses `Id`, `Parent` attributes, ``, ``, and `` elements. - **`DataAcquisitionSection`** - **`DataAcquisitionUnit[] DataAcquisitionUnits { get; }`**: Array of DAQ units. - **`void ReadXml(XmlElement element)`**: Parses a *single* `` element (note: despite the name, only one unit is supported per XML file per current implementation). - **`DataAcquisitionUnit`** - **Properties**: Extensive hardware metadata (e.g., `Name`, `Type`, `SerialNr`, `Manufacturer`, `SampleFrequencyHz`, `AnalogInputChannelCount`, `Trigger`, `Enabled`, `DataBaseUID`, etc.). - **`TriggerSection Trigger { get; }`**: Nested class with `TriggerMode`, `RecBus`, `T0Bus`, `Filter`. - **`AnalogInChannelSection AnalogChannels { get; }`**: Contains parsed analog input channels. - **`static DataAcquisitionUnit ReadXml(XmlElement root)`**: Parses all DAQ-specific XML elements. - Uses `GetDouble` helper (returns `NaN` on parse failure). - Handles nested `` and `` elements. - **`TriggerSection`** - **`void ReadXml(XmlElement root)`**: Parses ``, ``, ``, `` elements. - **`AnalogInChannelSection`** - **`AnalogInChannel[] Channels { get; }`**: Array of analog channels. - **`void ReadXml(XmlElement element)`**: Parses a *single* `` element. - **`AnalogInChannel`** - **Properties**: 50+ fields covering channel configuration, sensor details, calibration, and signal conditioning (e.g., `Enabled`, `Id`, `GroupId`, `ChannelName`, `BridgeType`, `Sensitivity`, `ExcitationVoltage`, `OffsetFlag`, `ShuntPosFlag`, `NextCalibrationDate`, `PhysicalUnit`, `Direction`, `InvertFlag`, `CalculatedGain`, `SensorStatusUsable`, `VoltageEngineeringUnit`). - **`static AnalogInChannel ReadXml(XmlElement root)`**: Parses all channel XML elements. - Uses `GetDate` helper (returns `DateTime.MinValue` on parse failure). - **Bug/Quirk**: In `ShuntPosMaxToleranceV` parsing, incorrectly assigns to `ShuntGainPos` instead of `ShuntPosMaxToleranceV` (see *Gotchas*). - **`static DateTime GetDate(string text)`** Helper for parsing `DateTime` from XML text (invariant culture, `DateTimeStyles.None`). Returns `DateTime.MinValue` on failure. - **`static double GetDouble(string text)`** Helper for parsing `double` from XML text (invariant culture, `NumberStyles.Any`). Returns `double.NaN` on failure. --- ### 3. Invariants - **XML Structure**: - Root element must be `` with a `Name` attribute. - Valid child elements under `` are strictly: ``, ``, ``. Unknown elements are logged but ignored. - `` supports only elements defined in `GeneralSection.Fields` enum. - `` must contain one or more `` elements. - `` must contain exactly one `` element (per current `ReadXml` implementation). - `` elements are parsed individually and appended to the channel list. - **Data Parsing**: - Numeric/date fields use `CultureInfo.InvariantCulture` for parsing. - Failure to parse numeric/date fields results in default values (`0`, `DateTime.MinValue`, `double.NaN`) and a `Trace.WriteLine` warning. - `Group` properties are stored in a dictionary; unknown keys are preserved. - `AnalogInChannel.Enabled`, `DataConversionEnabled`, etc., default to `false` if attribute/element missing. - **Object State**: - `General`, `ChannGroups`, `DataAcquisition` are initialized to non-null instances (via property initializers). - `Group.Groups`, `DataAcquisitionUnits`, `AnalogChannels.Channels` arrays are lazily populated via `ReadXml`. --- ### 4. Dependencies - **External Types**: - `System.Xml.XmlDocument`, `System.Xml.XmlElement`, `System.Xml.XmlNode` - `System.ComponentModel.DescriptionAttribute` (used in `Group.KnownFormats`) - `DTS.Common.Enums.Sensors.SensorConstants.BridgeType` (referenced in `GetEqxElectricalMethod`) - **Module Dependencies**: - This module *depends on* the `DTS.Common` assembly (for `BridgeType` enum). - *Used by*: Downstream components consuming `CrashDesignerTestSetup` objects (e.g., test execution, DAQ configuration, reporting). - **Notable**: The `DataAcquisitionSection` class has a commented-out property `public DataAcquisitionSection DataAcquisitionUnit { get; set; }`, suggesting a design change or legacy artifact. --- ### 5. Gotchas - **Shunt Parsing Bug**: In `AnalogInChannel.ReadXml`, the `ShuntPosMaxToleranceV` case incorrectly assigns to `ShuntGainPos` instead of `ShuntPosMaxToleranceV`: ```csharp case "ShuntPosMaxToleranceV": analog.ShuntGainPos = GetDouble(element.InnerText); break; // WRONG! ``` This will overwrite `ShuntGainPos` and leave `ShuntPosMaxToleranceV` at its default (`0`). **Impact**: Shunt calibration tolerance data may be corrupted. - **Single DAQ Unit Assumption**: `DataAcquisitionSection.ReadXml` only processes *one* `` element (appends to `_units` list once), despite the XML schema potentially supporting multiple. This may cause data loss if the input file contains multiple `` elements. - **Ambiguous `PreTriggerTimeReadout`/`PostTriggerTimeReadout`**: The XML element names (`PreTriggerTimeReadout`, `PostTriggerTimeReadout`) do not match the property names (`PreTriggerTime`, `PostTriggerTime`). This could confuse developers unfamiliar with the enum mapping. - **`KnownFormats` Enum Mismatch**: The `KnownFormats` enum uses `[Description]` attributes (e.g., `[Description("ISO Title")]`), but XML parsing for `Group` properties relies on `element.LocalName` matching the enum *name* (e.g., `ISOTitle`), not the description. This is correct per current code but may be error-prone. - **`GetEqxElectricalMethod` Behavior**: - `"Active"` and `"ActiveSensor"` both set `isProportional = false`, but the distinction is not documented. - `"PiezoInput"` is the *only* case that sets `bridgeType = IEPE`; other active bridges use `FullBridge`/`HalfBridge`/`QuarterBridge` with `isProportional = false`. - **No Validation**: The class performs no semantic validation (e.g., checking `SampleFrequencyHz` is within `MinSampleFrequencyHz`/`MaxSampleFrequencyHz`, or `GroupId` references exist). Invalid data may propagate silently. - **Missing `DataAcquisitionUnit` Property**: The commented-out property `public DataAcquisitionSection DataAcquisitionUnit { get; set; }` suggests confusion between `DataAcquisitionSection` (container) and `DataAcquisitionUnit` (item). The current design uses `DataAcquisition.DataAcquisitionUnits` (array), which is correct, but the commented line may indicate historical instability. - **No Error Handling for XML Load**: `ReadXML` calls `doc.Load(importFile)` without try/catch. File I/O errors (e.g., missing file, malformed XML) will throw unhandled exceptions. - **Culture Sensitivity**: While numeric/date parsing uses invariant culture, string comparisons (e.g., `element.LocalName == "General"`) are case-sensitive and culture-sensitive. XML element names must match *exactly* (e.g., `"General"`, not `"general"`).