CAN (控製器局域網) 為允許微控製器和設備在沒有主計算機的應用程序中相互通信,而設計的車輛總綫標準。
它是最初為汽車內多路復用電綫而設計,但也用於許多其它場閤的基於消息的協議。
CAN 總綫 API 為訪問 CAN 設備提供瞭一些公共 API:
多個供應商提供具有各種訪問 API 的 CAN 設備。 QtSerialBus 模塊支持下列 CAN 總綫插件集:
| 供應商 | 插件 (關鍵) | 簡要描述 |
|---|---|---|
| CAN over Linux sockets |
SocketCAN
(
socketcan
)
|
CAN 總綫插件使用 Linux sockets 和開源驅動程序。 |
| CAN via SAE J2534 Pass-Thru |
PassThruCAN
(
passthrucan
)
|
CAN 總綫插件使用 SAE J2534 Pass-Thru 接口。 |
| SYS TEC 電子 |
SystecCAN
(
systeccan
)
|
CAN 總綫後端使用 SYS TEC CAN 適配器。 |
| PEAK 係統 |
PeakCAN
(
peakcan
)
|
CAN 總綫插件使用 PEAK CAN 適配器。 |
| MHS 電子 |
TinyCAN
(
tinycan
)
|
CAN 總綫插件使用 MHS CAN 適配器。 |
| Vector Informatik |
VectorCAN
(
vectorcan
)
|
CAN 總綫插件使用 Vector CAN 適配器。 |
| 虛擬 CAN 接口 |
VirtualCAN
(
virtualcan
)
|
CAN 總綫插件使用虛擬 TCP/IP 連接。 |
If the plugins provided by Qt are not suitable for the required target platform, a custom CAN bus plugin can be implemented. The implementation follows the standard way of implementing Qt plug-ins. The custom plugin must be deployed to
$QTDIR/plugins/canbus
.
Each plugin must define a key, which is used to load the plugin. This is done via a small json file. For example, the socketcan plugin uses the following
plugin.json
:
{
"Key": "socketcan"
}
此鍵必須被傳遞給 QCanBus::createDevice () together with the interface name of the CAN bus adapter. QCanBus loads and instantiates the plugin using the QCanBusFactoryV2 interface which each plugin must implement as central entry point. The interface acts as a factory and its sole purpose is to return a QCanBusDevice instance. The above mentioned interface name is passed on via the factory's QCanBusFactory::createDevice () method. The following is the factory implementation of the socketcan 插件:
class SocketCanBusPlugin : public QObject, public QCanBusFactoryV2 { Q_OBJECT Q_PLUGIN_METADATA(IID "org.qt-project.Qt.QCanBusFactory" FILE "plugin.json") Q_INTERFACES(QCanBusFactoryV2) public: QList<QCanBusDeviceInfo> availableDevices(QString *errorMessage) const override { Q_UNUSED(errorMessage); return SocketCanBackend::interfaces(); } QCanBusDevice *createDevice(const QString &interfaceName, QString *errorMessage) const override { Q_UNUSED(errorMessage); auto device = new SocketCanBackend(interfaceName); return device; } };
The next step is to provide an implementation of QCanBusDevice . At the very least, the following pure virtual functions must be implemented:
The open() and close() methods are used in conjunction with QCanBusDevice::connectDevice () 和 QCanBusDevice::disconnectDevice () respectively. Check the function documentation for implementation details.
QCanBusDevice::writeFrame () is responsible for sanity checks such as the validity of the QCanBusFrame and that the device is still connected. Provided that the checks passed, it writes the frame to the CAN bus. Upon success it emits the QCanBusDevice::framesWritten () signal; otherwise QCanBusDevice::setError () is called with an appropriate error message. This function may also be used to implement an asynchronous write operation. It is the plugin implementors responsibility to emit the appropriate signals at the appropriate time.
最後但最重要, QCanBusDevice::interpretErrorFrame provides a convenient way to translate the content of an CAN bus error frame to a human-readable error string.