π Overview #
In hardware-in-the-loop (HIL) simulation, real-time determinism and reliable I/O are essential for validating complex cyber-physical systems such as armored vehicles, aerospace platforms, and autonomous systems. In 2014, researchers from the Northwest Institute of Mechanical and Electrical Engineering presented a practical implementation of a CAN2.0B device driver for the PCM3680 PCI CAN card, integrated into RT-LAB and QNX environments.
Published in Computer Measurement & Control (Vol. 22, No. 1), the work demonstrates how unsupported hardware can be integrated into a commercial real-time simulation framework through custom driver development. Although the implementation targets legacy hardware, the architectural principles remain relevant in 2025 for HIL platforms, defense simulations, and automotive test benches.
π§© RT-LAB and the Role of Custom Drivers #
RT-LAB, developed by Opal-RT Technologies, is a model-based real-time simulation platform widely used for HIL testing. It converts Matlab/Simulink or MATRIXx/SystemBuild models into C code and deploys them across a hostβtarget architecture:
- Host: Windows-based system for model editing, monitoring, and control
- Target: QNX-based real-time system executing deterministic simulation code
While RT-LAB provides built-in support for many I/O boards, unsupported hardware such as the PCM3680 CAN card requires custom drivers. These drivers act as the bridge between high-level simulation models and low-level hardware access under QNX.
π§΅ PCM3680 Hardware Overview #
The PCM3680 is a PCI-based CAN interface card designed for industrial control applications. Its main features include:
- CAN controller: Philips SJA1000, supporting CAN2.0A and CAN2.0B
- Electrical isolation: Opto-isolation for improved noise immunity
- Transceiver: 82C250 for CAN bus driving
- Memory-mapped I/O: Address range from 0xC8000 to 0xEFFFF
- 0x00β0xFF: SJA1000 registers
- 0x100β0x1FF: hardware reset region
- Interrupt configuration: Jumper-selectable IRQs (3β7, 9β12, 15)
This design allows flexible integration into PCI-based real-time targets while maintaining robust CAN communication.
π§ Upper-Layer Integration with Matlab S-Functions #
To expose CAN functionality to Simulink models, the driver uses S-Functions as the upper-layer interface. Each S-Function encapsulates a specific CAN operation and maps directly to QNX driver routines.
The driver is organized into four main S-Function blocks:
- Initialization block: Creates a CAN setup object, initializes hardware, configures bit timing and filters, and switches the controller into normal mode
- Send block: Packages simulation data into CAN frames and transmits them
- Receive block: Reads CAN frames from the driver and outputs them to the model
- External synchronization block: Attaches an interrupt service routine (ISR) to support external timing synchronization
This structure allows CAN communication to be seamlessly embedded into real-time simulation models.
βοΈ QNX Bottom-Layer Driver Architecture #
The core driver runs on QNX and is responsible for all direct hardware interactions. It is implemented as a resource manager and provides a clean abstraction layer for the S-Functions.
Data Structures #
The driver defines structured representations for CAN messages and configuration parameters:
typedef struct {
int sff;
BYTE id[4];
int rtr;
int dlen;
BYTE data[8];
} CANMSG;
typedef struct {
int filter_num;
BYTE acc_code[4];
BYTE acc_mask[4];
BYTE b0;
BYTE b1;
} CANCFG;
These structures support standard and extended frames, acceptance filtering, and configurable bit timing.
System-Level Services #
The implementation relies on key QNX services, including:
mmap_device_memoryfor mapping PCI memory regionsThreadCtl(_NTO_TCTL_IO)to enable I/O privilegesInterruptAttachandInterruptDetachfor ISR managementInterruptMaskandInterruptUnmaskfor fine-grained interrupt control
Access to shared registers is protected with mutexes to ensure thread safety.
Interrupt Handling #
Interrupt service routines are intentionally lightweight. For example, the synchronization ISR simply sets a flag that is later processed in task context:
const struct sigevent *sync_isr_all(void *area, int id) {
syncFlag = 1;
return NULL;
}
This design minimizes interrupt latency and preserves real-time performance.
π§ͺ Application and Validation #
The driver was deployed in a self-propelled gun HIL simulation system, where CAN communication connected simulation models to real hardware components. Long-duration tests demonstrated stable operation with no observed failures, confirming both functional correctness and real-time reliability.
π Relevance in 2025 #
Although developed over a decade ago, this work remains instructive. Many modern HIL systems still require custom driver development to integrate proprietary or legacy hardware. The combination of RT-LAB for model-based simulation and QNX for deterministic execution continues to be widely used in defense, automotive, and industrial domains.
The architectural approach outlined in this paper can be readily adapted to newer technologies such as CAN FD, higher-speed PCIe interfaces, or multicore QNX deployments. For engineers working on real-time simulation platforms, it provides a clear and practical blueprint for bridging high-level models with low-level hardware.