//
//  Licensed to the Apache Software Foundation (ASF) under one or more
//  contributor license agreements.  See the NOTICE file distributed with
//  this work for additional information regarding copyright ownership.
//  The ASF licenses this file to You under the Apache License, Version 2.0
//  (the "License"); you may not use this file except in compliance with
//  the License.  You may obtain a copy of the License at
//
//      https://www.apache.org/licenses/LICENSE-2.0
//
//  Unless required by applicable law or agreed to in writing, software
//  distributed under the License is distributed on an "AS IS" BASIS,
//  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
//  See the License for the specific language governing permissions and
//  limitations under the License.
//
:imagesdir: ../../images/users/protocols
:icons: font

= CAN Bus

image::users/protocols/can_banner.png[banner,512,167]

NOTE: This page describes how the CAN drivers are put together. There is no driver with the
protocol code `can` - connect with xref:protocols/canopen.adoc[CANopen] (`canopen`) or
xref:protocols/genericcan.adoc[GenericCAN] (`genericcan`) instead.

CAN differs from the other buses PLC4X supports in that the wire carries short, identifier-tagged
frames rather than a request/response stream. The transports own the bus access and hand the
drivers a uniform frame type; each driver then interprets those frames according to its own
application-layer protocol.

== Transport and frame model

The xref:transports/can.adoc[CAN transport facade] provides a single frame representation that
all CAN drivers work against:

* `CanFrame` (`plc4j/transports/can`) - an identifier, up to 8 data bytes, and the standard/extended
and remote-transmission-request flags. Standard identifiers are 11 bit (`MAX_STANDARD_ID`), extended
ones 29 bit (`MAX_EXTENDED_ID`).
* `CanFrameBuilder` - obtained from `CanFrame.builder()`, used by the drivers to construct outgoing
frames.
* `CanIdFilter` - lets a driver subscribe to a subset of identifiers instead of the whole bus.

Two transports implement this facade: `can-socketcan` (Linux SocketCAN, the usual choice on real
hardware) and `can-virtualcan` (an in-process bus, useful for tests and for running two PLC4X
components against each other without a physical interface).

== Driver structure

Each CAN driver is a `ConnectionBase` implementation that owns a message codec translating between
`CanFrame` and its own protocol frame:

* xref:protocols/canopen.adoc[CANopen] - `CANOpenConnection` with `CANOpenMessageCodec`, implementing the
CANopen service model (SDO, PDO, NMT, heartbeat).
* xref:protocols/genericcan.adoc[GenericCAN] - `GenericCANConnection`, which applies no application-layer
semantics at all and simply maps identifiers to typed payload slices.

Incoming frames arrive from the codec and are dispatched to the subscriptions registered for the
matching node id; outgoing writes are encoded and handed straight back to the codec.

NOTE: Earlier releases interposed a separate `CANDriverAdapter` between the transport and the
driver, with a `FrameData` interface and per-transport frame types such as `SocketCANFrame`. That
indirection was removed when the drivers were ported to the new SPI: the adapter's work is now done
by the driver's own connection class, and every transport produces a `CanFrame` directly.
