6#include "dawn/proto/can/isotp.hxx"
11#include "dawn/porting/can.hxx"
19void CIsoTp::initState(State &state)
28void CIsoTp::resetState(State &state)
36uint8_t CIsoTp::getFrameType(uint8_t pci)
38 return pci & FRAME_TYPE_MASK;
41uint8_t CIsoTp::getSequence(uint8_t pci)
43 return pci & SEQ_MASK;
46uint8_t CIsoTp::nextSequence(uint8_t seq)
48 return (seq + 1) & SEQ_MASK;
58 const uint8_t *payload;
67 total_len = msg.data[1];
68 if (total_len == 0 || total_len > buf_size)
75 payload = msg.data + 2;
76 payload_len = msg.len - 2;
78 if (payload_len > total_len)
80 payload_len = total_len;
85 state.total_len = total_len;
92 std::memcpy(data_buf, payload, payload_len);
93 state.offset = payload_len;
95 return static_cast<int>(payload_len);
105 const uint8_t *payload;
120 seq = getSequence(msg.data[0]);
121 if (seq != state.seq_next)
129 payload = msg.data + 1;
130 payload_len = msg.len - 1;
134 remaining = state.total_len - state.offset;
135 if (payload_len > remaining)
137 payload_len = remaining;
140 if (state.offset + payload_len > buf_size)
148 std::memcpy(
static_cast<uint8_t *
>(data_buf) + state.offset, payload, payload_len);
150 state.offset += payload_len;
151 state.seq_next = nextSequence(state.seq_next);
155 if (state.offset >= state.total_len)
160 return static_cast<int>(payload_len);
163bool CIsoTp::isComplete(
const State &state)
165 return state.active && (state.offset >= state.total_len);
168bool CIsoTp::isTimeout(
const State &state, uint64_t now, uint64_t timeout)
170 if (!state.active || timeout == 0)
175 return (now - state.timestamp) > timeout;
193 frame_type = getFrameType(msg.data[0]);
202 if (isTimeout(state, now, timeout))
212 ret = handleFirstFrame(msg, state, data_buf, buf_size);
218 state.timestamp = now;
224 ret = handleConsecutiveFrame(msg, state, data_buf, buf_size);
230 state.timestamp = now;
251 size_t payload_len = msg.len - 2;
263 state.timestamp = now;
265 else if (timeout > 0 && (now - state.timestamp) > timeout)
267 state.active =
false;
276 state.timestamp = now;
279 if (seg_no != state.seq_next)
281 state.active =
false;
285 if (state.offset + payload_len > buf_size)
287 state.active =
false;
291 std::memcpy(
static_cast<uint8_t *
>(data_buf) + state.offset, msg.data + 2, payload_len);
293 state.offset += payload_len;
294 state.timestamp = now;
298 if (state.offset != buf_size)
300 state.active =
false;
static int receiveCustom(const porting::canmsg_s &msg, State &state, void *data_buf, size_t buf_size, uint8_t seg_no, bool seg_last, uint64_t now, uint64_t timeout)
Process incoming Custom Segmented frame (Dawn specific).
static int receive(const porting::canmsg_s &msg, State &state, void *data_buf, size_t buf_size, uint64_t now, uint64_t timeout)
Process incoming ISO-TP frame.
static uint8_t FRAME_CF
Consecutive Frame (0x2N)
static uint8_t FRAME_FF
First Frame (0x1N)
Out-of-tree user-extension hooks for Dawn.
Common CAN message format for chardev and socketCAN.