ASCOM IDomeV2 Interface
Relevant source files
The following files were used as context for generating this wiki page:The Pulsar_DomeDriver project provides an ASCOM-compliant driver for the Pulsar dome. The core of this project is the DomeDriver class, which implements the ASCOM.DeviceInterface.IDomeV2 interface. This implementation facilitates communication with the dome controller hardware over a serial port, manages dome state, and exposes standard dome operations like slewing, opening/closing the shutter, parking, and homing to ASCOM-compatible astronomy software.
A key architectural feature of this driver is its robustness, achieved through a multi-layered system of status polling, command-specific action watchdogs, and an automated reset mechanism (both soft and hard) to recover from hardware stalls or communication failures. The driver also integrates with external systems like MQTT for status publishing and the Goodnight System (GNS) for user notifications.
System Architecture
The driver is composed of several key classes that work together to manage configuration, communication, state, and error handling.
Sources: Driver/Pulsar_DomeDriver.cs, Config/ConfigManager.cs, Helper/ActionWatchdog.cs, Helper/SerialPortGuard.cs, MQTT/MqttPublisher.cs, GNS/GNS.cs, Diagnostics/FileLogger.cs
Core Components
The following diagram illustrates the primary classes and their relationships.
DomeDriver*: The main class implementing the IDomeV2 interface. It orchestrates all operations.
- ConfigManager: Manages all driver settings, reading from and writing to the ASCOM profile. It also holds the volatile state of the dome (e.g.,
Azimuth,ShutterStatus). - SerialPortGuard: A helper class that ensures thread-safe, exclusive access to the
SerialPortfor sending commands and receiving responses. - ActionWatchdog: Monitors long-running operations (like slewing or shutter movement). If an action does not complete within its timeout, it can trigger the
ResetRoutineAsync. - MqttPublisher: Publishes dome status and events to an MQTT broker if enabled.
- GNS: Sends notifications to the Goodnight System (GNS) if enabled.
- FileLogger: Provides file-based logging for diagnostics.
Sources: Driver/Pulsar_DomeDriver.cs:25, Config/ConfigManager.cs:18, Helper/SerialPortGuard.cs:11, Helper/ActionWatchdog.cs:10, MQTT/MqttPublisher.cs:12, GNS/GNS.cs:15, Diagnostics/FileLogger.cs:9
Configuration
Driver settings are managed by the ConfigManager class and stored in the ASCOM profile under the Pulsar_DomeDriver ProgID. A graphical user interface, SettingsForm, is provided for user configuration.
Sources: Config/ConfigManager.cs, UI/SettingsForm.cs
Key Configuration Settings
| Setting | Type | Description | Source File |
|---|---|---|---|
SerialPort | string | The COM port for communicating with the dome controller. | ConfigManager.cs:88-92 |
LogLocation | string | The directory path for storing log files. | ConfigManager.cs:124-128 |
SoftReset | bool | Enables the internal RESTART command for recovery. | ConfigManager.cs:94-103 |
HardReset | bool | Enables external executable-based power-cycling for recovery. | ConfigManager.cs:105-114 |
ResetExe | string | Path to the executable used for a hard reset. | ConfigManager.cs:129-133 |
ResetOnParameters | string | Command-line arguments for the "ON" phase of a hard reset. | ConfigManager.cs:135-139 |
ResetOffParameters | string | Command-line arguments for the "OFF" phase of a hard reset. | ConfigManager.cs:141-145 |
ResetDelay | int | Delay (in ms) to wait for the controller to come online after a hard reset. | ConfigManager.cs:147-157 |
CycleDelay | int | Delay (in ms) between the "OFF" and "ON" phases of a hard reset. | ConfigManager.cs:159-169 |
ShutterTimeout | int | Timeout (in ms) for shutter open/close operations. | ConfigManager.cs:171-185 |
RotationTimeout | int | Timeout (in ms) for dome rotation (slew/home/park) operations. | ConfigManager.cs:187-201 |
DebugLog | bool | Enables detailed debug-level logging. | ConfigManager.cs:203-212 |
TraceLog | bool | Enables highly verbose trace-level logging. | ConfigManager.cs:214-223 |
UseMQTT | bool | Enables publishing status messages to an MQTT broker. | ConfigManager.cs:225-234 |
UseGNS | bool | Enables sending notifications to the Goodnight System. | ConfigManager.cs:236-245 |
Connection and Communication
Connection Lifecycle
The Connected property in DomeDriver manages the entire connection lifecycle. Setting it to true initiates a connection sequence, while setting it to false triggers disconnection.
The following diagram shows the sequence of events when establishing a connection.
Serial Communication
All serial communication is mediated by the SerialPortGuard class. It uses a SemaphoreSlim to ensure that only one command is sent at a time, preventing contention on the serial port from multiple threads. The Send method handles writing the command, waiting for a response, and managing timeouts.
The DomeDriver.SendAndVerify method provides a higher-level wrapper around SerialPortGuard.Send to validate responses. It supports several modes defined by the ResponseMode enum.
| Mode | Description |
|---|---|
Blind | Sends a command without waiting for or reading a response. |
Raw | Sends a command and returns the raw string response. |
MatchExact | Checks if the response exactly matches a single expected string. |
MatchAny | Checks if the response matches any string in a list of expected responses. |
Sources: Helper/SerialPortGuard.cs:11-88, Driver/Pulsar_DomeDriver.cs:1356-1449, Config/ConfigManager.cs:20-26
Status Polling and Watchdogs
The driver's stability relies on a continuous polling loop and two types of watchdogs.
Status Polling Loop
Once connected, StartPolling launches a background task (PollLoopAsync) that periodically calls DomeStatus. This method sends commands to the controller to get the latest azimuth, shutter state, and home/park status. This loop is the primary mechanism for updating the driver's internal state. The polling interval is configurable via _config._pollingIntervalMs.
Sources: Driver/Pulsar_DomeDriver.cs:511-645
System Watchdog
A system-level watchdog (StartWatchdog) runs in parallel to the polling loop. It checks if the _lastPollTimestamp has been updated recently. If the timestamp is older than a threshold (_pollingStallThreshold), it assumes the polling loop has stalled and forcefully restarts it. This ensures the driver remains responsive even if the polling task hangs. It also publishes a periodic MQTT heartbeat.
Sources: Driver/Pulsar_DomeDriver.cs:647-703
This diagram shows the interaction between the polling loop and the system watchdog.
Sources: Driver/Pulsar_DomeDriver.cs:511-703
Command Execution and Recovery
Dome actions like slewing or opening the shutter are handled by a generic ExecuteDomeCommand method, which centralizes command dispatch, state updates, and watchdog management.
Command Execution Flow
When a command like SlewToAzimuth is called:
- The
ExecuteDomeCommandmethod is invoked with parameters specific to the action (command string, timeout, success conditions). - Polling is temporarily stopped to prevent interference.
- The command is sent to the controller via
SendAndVerify. - If the command is acknowledged, an
ActionWatchdogis started to monitor its completion. - Polling is resumed. The polling loop is now responsible for detecting the final state (e.g., dome has reached target azimuth) and marking the watchdog as successful.
The following diagram illustrates the sequence for a SlewToAzimuth command.
Error Handling and Reset Routine
The ActionWatchdog is crucial for error recovery. If an action does not complete within its specified timeout, the watchdog triggers the ResetRoutineAsync method.
The reset routine is a multi-stage process designed to recover a non-responsive controller:
- Soft Reset: If enabled (
SoftReset = true), it sends aRESTARTcommand to the controller. - Hard Reset: If the soft reset is disabled or fails, and hard reset is enabled (
HardReset = true), it executes an external program (ResetExe) to power-cycle the dome controller. This involves separate "OFF" and "ON" commands. - Replay Command: After a successful reset, the driver attempts to replay the last command that failed.
This flow ensures that the driver makes a best effort to recover from hardware or communication faults without manual intervention.
ASCOM IDomeV2 Implementation
The DomeDriver class implements the properties, methods, and capabilities required by the IDomeV2 interface.
Capabilities
| Capability | Supported | Source |
|---|---|---|
CanFindHome | Yes | Driver/Pulsar_DomeDriver.cs:1516 |
CanPark | Yes | Driver/Pulsar_DomeDriver.cs:1517 |
CanSetAzimuth | Yes | Driver/Pulsar_DomeDriver.cs:1518 |
CanSetAltitude | No | Driver/Pulsar_DomeDriver.cs:1519 |
CanSetShutter | Yes | Driver/Pulsar_DomeDriver.cs:1520 |
CanSyncAzimuth | No | Driver/Pulsar_DomeDriver.cs:1521 |
CanSetPark | Yes | Driver/Pulsar_DomeDriver.cs:1522 |
CanSlave | No | Driver/Pulsar_DomeDriver.cs:1523 |
Properties
| Property | Description | Source |
|---|---|---|
Altitude | Not supported. Throws MethodNotImplementedException. | Driver/Pulsar_DomeDriver.cs:1528-1534 |
Azimuth | Gets the current dome azimuth in degrees from _config.Azimuth. | Driver/Pulsar_DomeDriver.cs:1535-1543 |
AtHome | Gets the home status from _config.HomeStatus. | Driver/Pulsar_DomeDriver.cs:1544-1552 |
AtPark | Gets the park status from _config.ParkStatus. | Driver/Pulsar_DomeDriver.cs:1553-1561 |
ShutterStatus | Returns the shutter state (Open, Closed, Opening, Closing, Error). | Driver/Pulsar_DomeDriver.cs:1562-1576 |
Slaved | Not supported. Throws MethodNotImplementedException. | Driver/Pulsar_DomeDrivercs:1577-1584 |
Slewing | Returns true if the dome or shutter is currently moving. | Driver/Pulsar_DomeDriver.cs:1585-1593 |
Methods
| Method | Description | Source |
|---|---|---|
AbortSlew() | Sends a STOP command to the controller to halt all movement. | Driver/Pulsar_DomeDriver.cs:1865-1915 |
CloseShutter() | Initiates shutter closing via ExecuteDomeCommand. | Driver/Pulsar_DomeDriver.cs:1742-1767 |
FindHome() | Initiates a homing sequence via ExecuteDomeCommand. | Driver/Pulsar_DomeDriver.cs:1807-1835 |
OpenShutter() | Initiates shutter opening via ExecuteDomeCommand. | Driver/Pulsar_DomeDriver.cs:1716-1740 |
| s | Park() | Initiates a parking sequence via ExecuteDomeCommand. |
SetPark() | Defines the current position as the park position. (Logic is a placeholder). | Driver/Pulsar_DomeDriver.cs:1923-1927 |
SlewToAzimuth(double) | Slews the dome to a specific azimuth via ExecuteDomeCommand. | Driver/Pulsar_DomeDriver.cs:1768-1805 |
SyncToAzimuth(double) | Not supported. Throws MethodNotImplementedException. | Driver/Pulsar_DomeDriver.cs:1917-1922 |
Action(string, string) | Supports custom actions: "Full Reset", "Soft Reset", "Hard Reset". | Driver/Pulsar_DomeDriver.cs:2000-2020 |
Summary
The Pulsar_DomeDriver provides a comprehensive and resilient implementation of the ASCOM IDomeV2 interface. Its architecture is defined by a clear separation of concerns: configuration management, thread-safe serial communication, and state management. The most significant feature is its robust error recovery system, which combines a multi-level watchdog strategy with an automated, configurable reset routine. This allows the driver to autonomously recover from common hardware and communication failures, making it a reliable component in an automated observatory environment.
Sources: Driver/Pulsar_DomeDriver.cs, Config/ConfigManager.cs, Helper/ActionWatchdog.cs```
Relevant source files
The following files were used as context for generating this wiki page:The Pulsar_DomeDriver project provides an ASCOM-compliant driver for the Pulsar dome. The core of this project is the DomeDriver class, which implements the ASCOM.DeviceInterface.IDomeV2 interface. This implementation facilitates communication with the dome controller hardware over a serial port, manages dome state, and exposes standard dome operations like slewing, opening/closing the shutter, parking, and homing to ASCOM-compatible astronomy software.
A key architectural feature of this driver is its robustness, achieved through a multi-layered system of status polling, command-specific action watchdogs, and an automated reset mechanism (both soft and hard) to recover from hardware stalls or communication failures. The driver also integrates with external systems like MQTT for status publishing and the Goodnight System (GNS) for user notifications.
System Architecture
The driver is composed of several key classes that work together to manage configuration, communication, state, and error handling.
Sources: Driver/Pulsar_DomeDriver.cs, Config/ConfigManager.cs, Helper/ActionWatchdog.cs, Helper/SerialPortGuard.cs, MQTT/MqttPublisher.cs, GNS/GNS.cs, Diagnostics/FileLogger.cs
Core Components
The following diagram illustrates the primary classes and their relationships.
DomeDriver*: The main class implementing the IDomeV2 interface. It orchestrates all operations.
- ConfigManager: Manages all driver settings, reading from and writing to the ASCOM profile. It also holds the volatile state of the dome (e.g.,
Azimuth,ShutterStatus). - SerialPortGuard: A helper class that ensures thread-safe, exclusive access to the
SerialPortfor sending commands and receiving responses. - ActionWatchdog: Monitors long-running operations (like slewing or shutter movement). If an action does not complete within its timeout, it can trigger the
ResetRoutineAsync. - MqttPublisher: Publishes dome status and events to an MQTT broker if enabled.
- GNS: Sends notifications to the Goodnight System (GNS) if enabled.
- FileLogger: Provides file-based logging for diagnostics.
Sources: Driver/Pulsar_DomeDriver.cs:25, Config/ConfigManager.cs:18, Helper/SerialPortGuard.cs:11, Helper/ActionWatchdog.cs:10, MQTT/MqttPublisher.cs:12, GNS/GNS.cs:15, Diagnostics/FileLogger.cs:9
Configuration
Driver settings are managed by the ConfigManager class and stored in the ASCOM profile under the Pulsar_DomeDriver ProgID. A graphical user interface, SettingsForm, is provided for user configuration.
Sources: Config/ConfigManager.cs, UI/SettingsForm.cs
Key Configuration Settings
| Setting | Type | Description | Source File |
|---|---|---|---|
SerialPort | string | The COM port for communicating with the dome controller. | ConfigManager.cs:88-92 |
LogLocation | string | The directory path for storing log files. | ConfigManager.cs:124-128 |
SoftReset | bool | Enables the internal RESTART command for recovery. | ConfigManager.cs:94-103 |
HardReset | bool | Enables external executable-based power-cycling for recovery. | ConfigManager.cs:105-114 |
ResetExe | string | Path to the executable used for a hard reset. | ConfigManager.cs:129-133 |
ResetOnParameters | string | Command-line arguments for the "ON" phase of a hard reset. | ConfigManager.cs:135-139 |
ResetOffParameters | string | Command-line arguments for the "OFF" phase of a hard reset. | ConfigManager.cs:141-145 |
ResetDelay | int | Delay (in ms) to wait for the controller to come online after a hard reset. | ConfigManager.cs:147-157 |
CycleDelay | int | Delay (in ms) between the "OFF" and "ON" phases of a hard reset. | ConfigManager.cs:159-169 |
ShutterTimeout | int | Timeout (in ms) for shutter open/close operations. | ConfigManager.cs:171-185 |
RotationTimeout | int | Timeout (in ms) for dome rotation (slew/home/park) operations. | ConfigManager.cs:187-201 |
DebugLog | bool | Enables detailed debug-level logging. | ConfigManager.cs:203-212 |
TraceLog | bool | Enables highly verbose trace-level logging. | ConfigManager.cs:214-223 |
UseMQTT | bool | Enables publishing status messages to an MQTT broker. | ConfigManager.cs:225-234 |
UseGNS | bool | Enables sending notifications to the Goodnight System. | ConfigManager.cs:236-245 |
Connection and Communication
Connection Lifecycle
The Connected property in DomeDriver manages the entire connection lifecycle. Setting it to true initiates a connection sequence, while setting it to false triggers disconnection.
The following diagram shows the sequence of events when establishing a connection.
Serial Communication
All serial communication is mediated by the SerialPortGuard class. It uses a SemaphoreSlim to ensure that only one command is sent at a time, preventing contention on the serial port from multiple threads. The Send method handles writing the command, waiting for a response, and managing timeouts.
The DomeDriver.SendAndVerify method provides a higher-level wrapper around SerialPortGuard.Send to validate responses. It supports several modes defined by the ResponseMode enum.
| Mode | Description |
|---|---|
Blind | Sends a command without waiting for or reading a response. |
Raw | Sends a command and returns the raw string response. |
MatchExact | Checks if the response exactly matches a single expected string. |
MatchAny | Checks if the response matches any string in a list of expected responses. |
Sources: Helper/SerialPortGuard.cs:11-88, Driver/Pulsar_DomeDriver.cs:1356-1449, Config/ConfigManager.cs:20-26
Status Polling and Watchdogs
The driver's stability relies on a continuous polling loop and two types of watchdogs.
Status Polling Loop
Once connected, StartPolling launches a background task (PollLoopAsync) that periodically calls DomeStatus. This method sends commands to the controller to get the latest azimuth, shutter state, and home/park status. This loop is the primary mechanism for updating the driver's internal state. The polling interval is configurable via _config._pollingIntervalMs.
Sources: Driver/Pulsar_DomeDriver.cs:511-645
System Watchdog
A system-level watchdog (StartWatchdog) runs in parallel to the polling loop. It checks if the _lastPollTimestamp has been updated recently. If the timestamp is older than a threshold (_pollingStallThreshold), it assumes the polling loop has stalled and forcefully restarts it. This ensures the driver remains responsive even if the polling task hangs. It also publishes a periodic MQTT heartbeat.
Sources: Driver/Pulsar_DomeDriver.cs:647-703
This diagram shows the interaction between the polling loop and the system watchdog.
Sources: Driver/Pulsar_DomeDriver.cs:511-703
Command Execution and Recovery
Dome actions like slewing or opening the shutter are handled by a generic ExecuteDomeCommand method, which centralizes command dispatch, state updates, and watchdog management.
Command Execution Flow
When a command like SlewToAzimuth is called:
- The
ExecuteDomeCommandmethod is invoked with parameters specific to the action (command string, timeout, success conditions). - Polling is temporarily stopped to prevent interference.
- The command is sent to the controller via
SendAndVerify. - If the command is acknowledged, an
ActionWatchdogis started to monitor its completion. - Polling is resumed. The polling loop is now responsible for detecting the final state (e.g., dome has reached target azimuth) and marking the watchdog as successful.
The following diagram illustrates the sequence for a SlewToAzimuth command.
Error Handling and Reset Routine
The ActionWatchdog is crucial for error recovery. If an action does not complete within its specified timeout, the watchdog triggers the ResetRoutineAsync method.
The reset routine is a multi-stage process designed to recover a non-responsive controller:
- Soft Reset: If enabled (
SoftReset = true), it sends aRESTARTcommand to the controller. - Hard Reset: If the soft reset is disabled or fails, and hard reset is enabled (
HardReset = true), it executes an external program (ResetExe) to power-cycle the dome controller. This involves separate "OFF" and "ON" commands. - Replay Command: After a successful reset, the driver attempts to replay the last command that failed.
This flow ensures that the driver makes a best effort to recover from hardware or communication faults without manual intervention.
ASCOM IDomeV2 Implementation
The DomeDriver class implements the properties, methods, and capabilities required by the IDomeV2 interface.
Capabilities
| Capability | Supported | Source |
|---|---|---|
CanFindHome | Yes | Driver/Pulsar_DomeDriver.cs:1516 |
CanPark | Yes | Driver/Pulsar_DomeDriver.cs:1517 |
CanSetAzimuth | Yes | Driver/Pulsar_DomeDriver.cs:1518 |
CanSetAltitude | No | Driver/Pulsar_DomeDriver.cs:1519 |
CanSetShutter | Yes | Driver/Pulsar_DomeDriver.cs:1520 |
CanSyncAzimuth | No | Driver/Pulsar_DomeDriver.cs:1521 |
CanSetPark | Yes | Driver/Pulsar_DomeDriver.cs:1522 |
CanSlave | No | Driver/Pulsar_DomeDriver.cs:1523 |
Properties
| Property | Description | Source |
|---|---|---|
Altitude | Not supported. Throws MethodNotImplementedException. | Driver/Pulsar_DomeDriver.cs:1528-1534 |
Azimuth | Gets the current dome azimuth in degrees from _config.Azimuth. | Driver/Pulsar_DomeDriver.cs:1535-1543 |
AtHome | Gets the home status from _config.HomeStatus. | Driver/Pulsar_DomeDriver.cs:1544-1552 |
AtPark | Gets the park status from _config.ParkStatus. | Driver/Pulsar_DomeDriver.cs:1553-1561 |
ShutterStatus | Returns the shutter state (Open, Closed, Opening, Closing, Error). | Driver/Pulsar_DomeDriver.cs:1562-1576 |
Slaved | Not supported. Throws MethodNotImplementedException. | Driver/Pulsar_DomeDrivercs:1577-1584 |
Slewing | Returns true if the dome or shutter is currently moving. | Driver/Pulsar_DomeDriver.cs:1585-1593 |
Methods
| Method | Description | Source |
|---|---|---|
AbortSlew() | Sends a STOP command to the controller to halt all movement. | Driver/Pulsar_DomeDriver.cs:1865-1915 |
CloseShutter() | Initiates shutter closing via ExecuteDomeCommand. | Driver/Pulsar_DomeDriver.cs:1742-1767 |
FindHome() | Initiates a homing sequence via ExecuteDomeCommand. | Driver/Pulsar_DomeDriver.cs:1807-1835 |
OpenShutter() | Initiates shutter opening via ExecuteDomeCommand. | Driver/Pulsar_DomeDriver.cs:1716-1740 |
| s | Park() | Initiates a parking sequence via ExecuteDomeCommand. |
SetPark() | Defines the current position as the park position. (Logic is a placeholder). | Driver/Pulsar_DomeDriver.cs:1923-1927 |
SlewToAzimuth(double) | Slews the dome to a specific azimuth via ExecuteDomeCommand. | Driver/Pulsar_DomeDriver.cs:1768-1805 |
SyncToAzimuth(double) | Not supported. Throws MethodNotImplementedException. | Driver/Pulsar_DomeDriver.cs:1917-1922 |
Action(string, string) | Supports custom actions: "Full Reset", "Soft Reset", "Hard Reset". | Driver/Pulsar_DomeDriver.cs:2000-2020 |
Summary
The Pulsar_DomeDriver provides a comprehensive and resilient implementation of the ASCOM IDomeV2 interface. Its architecture is defined by a clear separation of concerns: configuration management, thread-safe serial communication, and state management. The most significant feature is its robust error recovery system, which combines a multi-level watchdog strategy with an automated, configurable reset routine. This allows the driver to autonomously recover from common hardware and communication failures, making it a reliable component in an automated observatory environment.
Sources: Driver/Pulsar_DomeDriver.cs, Config/ConfigManager.cs, Helper/ActionWatchdog.cs