Skip to content

Commit ea78005

Browse files
hartkoppmarckleinebudde
authored andcommitted
can: add optional DLC element to Classical CAN frame structure
ISO 11898-1 Chapter 8.4.2.3 defines a 4 bit data length code (DLC) table which maps the DLC to the payload length of the CAN frame in bytes: DLC -> payload length 0 .. 8 -> 0 .. 8 9 .. 15 -> 8 Although the DLC values 8 .. 15 in Classical CAN always result in a payload length of 8 bytes these DLC values are transparently transmitted on the CAN bus. As the struct can_frame only provides a 'len' element (formerly 'can_dlc') which contains the plain payload length ( 0 .. 8 ) of the CAN frame, the raw DLC is not visible to the application programmer, e.g. for testing use-cases. To access the raw DLC values 9 .. 15 the len8_dlc element is introduced, which is only valid when the payload length 'len' is 8 and the DLC is greater than 8. The len8_dlc element is filled by the CAN interface driver and used for CAN frame creation by the CAN driver when the CAN_CTRLMODE_CC_LEN8_DLC flag is supported by the driver and enabled via netlink configuration interface. Reported-by: Vincent Mailhol <mailhol.vincent@wanadoo.fr> Signed-off-by: Oliver Hartkopp <socketcan@hartkopp.net> Link: https://lore.kernel.org/r/20201110101852.1973-2-socketcan@hartkopp.net Signed-off-by: Marc Kleine-Budde <mkl@pengutronix.de>
1 parent b7d3c0e commit ea78005

File tree

2 files changed

+25
-14
lines changed

2 files changed

+25
-14
lines changed

include/uapi/linux/can.h

Lines changed: 24 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -84,30 +84,40 @@ typedef __u32 can_err_mask_t;
8484

8585
/* CAN payload length and DLC definitions according to ISO 11898-1 */
8686
#define CAN_MAX_DLC 8
87+
#define CAN_MAX_RAW_DLC 15
8788
#define CAN_MAX_DLEN 8
8889

8990
/* CAN FD payload length and DLC definitions according to ISO 11898-7 */
9091
#define CANFD_MAX_DLC 15
9192
#define CANFD_MAX_DLEN 64
9293

9394
/**
94-
* struct can_frame - basic CAN frame structure
95-
* @can_id: CAN ID of the frame and CAN_*_FLAG flags, see canid_t definition
96-
* @can_dlc: frame payload length in byte (0 .. 8) aka data length code
97-
* N.B. the DLC field from ISO 11898-1 Chapter 8.4.2.3 has a 1:1
98-
* mapping of the 'data length code' to the real payload length
99-
* @__pad: padding
100-
* @__res0: reserved / padding
101-
* @__res1: reserved / padding
102-
* @data: CAN frame payload (up to 8 byte)
95+
* struct can_frame - Classical CAN frame structure (aka CAN 2.0B)
96+
* @can_id: CAN ID of the frame and CAN_*_FLAG flags, see canid_t definition
97+
* @len: CAN frame payload length in byte (0 .. 8)
98+
* @can_dlc: deprecated name for CAN frame payload length in byte (0 .. 8)
99+
* @__pad: padding
100+
* @__res0: reserved / padding
101+
* @len8_dlc: optional DLC value (9 .. 15) at 8 byte payload length
102+
* len8_dlc contains values from 9 .. 15 when the payload length is
103+
* 8 bytes but the DLC value (see ISO 11898-1) is greater then 8.
104+
* CAN_CTRLMODE_CC_LEN8_DLC flag has to be enabled in CAN driver.
105+
* @data: CAN frame payload (up to 8 byte)
103106
*/
104107
struct can_frame {
105108
canid_t can_id; /* 32 bit CAN_ID + EFF/RTR/ERR flags */
106-
__u8 can_dlc; /* frame payload length in byte (0 .. CAN_MAX_DLEN) */
107-
__u8 __pad; /* padding */
108-
__u8 __res0; /* reserved / padding */
109-
__u8 __res1; /* reserved / padding */
110-
__u8 data[CAN_MAX_DLEN] __attribute__((aligned(8)));
109+
union {
110+
/* CAN frame payload length in byte (0 .. CAN_MAX_DLEN)
111+
* was previously named can_dlc so we need to carry that
112+
* name for legacy support
113+
*/
114+
__u8 len;
115+
__u8 can_dlc; /* deprecated */
116+
};
117+
__u8 __pad; /* padding */
118+
__u8 __res0; /* reserved / padding */
119+
__u8 len8_dlc; /* optional DLC for 8 byte payload length (9 .. 15) */
120+
__u8 data[CAN_MAX_DLEN] __attribute__((aligned(8)));
111121
};
112122

113123
/*

include/uapi/linux/can/netlink.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -100,6 +100,7 @@ struct can_ctrlmode {
100100
#define CAN_CTRLMODE_FD 0x20 /* CAN FD mode */
101101
#define CAN_CTRLMODE_PRESUME_ACK 0x40 /* Ignore missing CAN ACKs */
102102
#define CAN_CTRLMODE_FD_NON_ISO 0x80 /* CAN FD in non-ISO mode */
103+
#define CAN_CTRLMODE_CC_LEN8_DLC 0x100 /* Classic CAN DLC option */
103104

104105
/*
105106
* CAN device statistics

0 commit comments

Comments
 (0)