1 /*
2  * Copyright (c) 2018 Karsten Koenig
3  *
4  * SPDX-License-Identifier: Apache-2.0
5  */
6 
7 #define DT_DRV_COMPAT microchip_mcp2515
8 
9 #include <kernel.h>
10 #include <device.h>
11 #include <drivers/spi.h>
12 #include <drivers/gpio.h>
13 
14 #define LOG_LEVEL CONFIG_CAN_LOG_LEVEL
15 #include <logging/log.h>
16 LOG_MODULE_REGISTER(mcp2515_can);
17 
18 #include "can_mcp2515.h"
19 #include "can_utils.h"
20 
21 #define SP_IS_SET(inst) DT_INST_NODE_HAS_PROP(inst, sample_point) ||
22 
23 /* Macro to exclude the sample point algorithm from compilation if not used
24  * Without the macro, the algorithm would always waste ROM
25  */
26 #define USE_SP_ALGO (DT_INST_FOREACH_STATUS_OKAY(SP_IS_SET) 0)
27 
28 #define SP_AND_TIMING_NOT_SET(inst) \
29 	(!DT_INST_NODE_HAS_PROP(inst, sample_point) && \
30 	!(DT_INST_NODE_HAS_PROP(inst, prop_seg) && \
31 	DT_INST_NODE_HAS_PROP(inst, phase_seg1) && \
32 	DT_INST_NODE_HAS_PROP(inst, phase_seg2))) ||
33 
34 #if DT_INST_FOREACH_STATUS_OKAY(SP_AND_TIMING_NOT_SET) 0
35 #error You must either set a sampling-point or timings (phase-seg* and prop-seg)
36 #endif
37 
mcp2515_cmd_soft_reset(const struct device * dev)38 static int mcp2515_cmd_soft_reset(const struct device *dev)
39 {
40 	uint8_t cmd_buf[] = { MCP2515_OPCODE_RESET };
41 
42 	const struct spi_buf tx_buf = {
43 		.buf = cmd_buf, .len = sizeof(cmd_buf),
44 	};
45 	const struct spi_buf_set tx = {
46 		.buffers = &tx_buf, .count = 1U
47 	};
48 
49 	return spi_write_dt(&DEV_CFG(dev)->bus, &tx);
50 }
51 
mcp2515_cmd_bit_modify(const struct device * dev,uint8_t reg_addr,uint8_t mask,uint8_t data)52 static int mcp2515_cmd_bit_modify(const struct device *dev, uint8_t reg_addr,
53 				  uint8_t mask,
54 				  uint8_t data)
55 {
56 	uint8_t cmd_buf[] = { MCP2515_OPCODE_BIT_MODIFY, reg_addr, mask, data };
57 
58 	const struct spi_buf tx_buf = {
59 		.buf = cmd_buf, .len = sizeof(cmd_buf),
60 	};
61 	const struct spi_buf_set tx = {
62 		.buffers = &tx_buf, .count = 1U
63 	};
64 
65 	return spi_write_dt(&DEV_CFG(dev)->bus, &tx);
66 }
67 
mcp2515_cmd_write_reg(const struct device * dev,uint8_t reg_addr,uint8_t * buf_data,uint8_t buf_len)68 static int mcp2515_cmd_write_reg(const struct device *dev, uint8_t reg_addr,
69 				 uint8_t *buf_data, uint8_t buf_len)
70 {
71 	uint8_t cmd_buf[] = { MCP2515_OPCODE_WRITE, reg_addr };
72 
73 	struct spi_buf tx_buf[] = {
74 		{ .buf = cmd_buf, .len = sizeof(cmd_buf) },
75 		{ .buf = buf_data, .len = buf_len }
76 	};
77 	const struct spi_buf_set tx = {
78 		.buffers = tx_buf, .count = ARRAY_SIZE(tx_buf)
79 	};
80 
81 	return spi_write_dt(&DEV_CFG(dev)->bus, &tx);
82 }
83 
84 /*
85  * Load TX buffer instruction
86  *
87  * When loading a transmit buffer, reduces the overhead of a normal WRITE
88  * command by placing the Address Pointer at one of six locations, as
89  * selected by parameter abc.
90  *
91  *   0: TX Buffer 0, Start at TXB0SIDH (0x31)
92  *   1: TX Buffer 0, Start at TXB0D0 (0x36)
93  *   2: TX Buffer 1, Start at TXB1SIDH (0x41)
94  *   3: TX Buffer 1, Start at TXB1D0 (0x46)
95  *   4: TX Buffer 2, Start at TXB2SIDH (0x51)
96  *   5: TX Buffer 2, Start at TXB2D0 (0x56)
97  */
mcp2515_cmd_load_tx_buffer(const struct device * dev,uint8_t abc,uint8_t * buf_data,uint8_t buf_len)98 static int mcp2515_cmd_load_tx_buffer(const struct device *dev, uint8_t abc,
99 				      uint8_t *buf_data, uint8_t buf_len)
100 {
101 	__ASSERT(abc <= 5, "abc <= 5");
102 
103 	uint8_t cmd_buf[] = { MCP2515_OPCODE_LOAD_TX_BUFFER | abc };
104 
105 	struct spi_buf tx_buf[] = {
106 		{ .buf = cmd_buf, .len = sizeof(cmd_buf) },
107 		{ .buf = buf_data, .len = buf_len }
108 	};
109 	const struct spi_buf_set tx = {
110 		.buffers = tx_buf, .count = ARRAY_SIZE(tx_buf)
111 	};
112 
113 	return spi_write_dt(&DEV_CFG(dev)->bus, &tx);
114 }
115 
116 /*
117  * Request-to-Send Instruction
118  *
119  * Parameter nnn is the combination of bits at positions 0, 1 and 2 in the RTS
120  * opcode that respectively initiate transmission for buffers TXB0, TXB1 and
121  * TXB2.
122  */
mcp2515_cmd_rts(const struct device * dev,uint8_t nnn)123 static int mcp2515_cmd_rts(const struct device *dev, uint8_t nnn)
124 {
125 	__ASSERT(nnn < BIT(MCP2515_TX_CNT), "nnn < BIT(MCP2515_TX_CNT)");
126 
127 	uint8_t cmd_buf[] = { MCP2515_OPCODE_RTS | nnn };
128 
129 	struct spi_buf tx_buf[] = {
130 		{ .buf = cmd_buf, .len = sizeof(cmd_buf) }
131 	};
132 	const struct spi_buf_set tx = {
133 		.buffers = tx_buf, .count = ARRAY_SIZE(tx_buf)
134 	};
135 
136 	return spi_write_dt(&DEV_CFG(dev)->bus, &tx);
137 }
138 
mcp2515_cmd_read_reg(const struct device * dev,uint8_t reg_addr,uint8_t * buf_data,uint8_t buf_len)139 static int mcp2515_cmd_read_reg(const struct device *dev, uint8_t reg_addr,
140 				uint8_t *buf_data, uint8_t buf_len)
141 {
142 	uint8_t cmd_buf[] = { MCP2515_OPCODE_READ, reg_addr };
143 
144 	struct spi_buf tx_buf[] = {
145 		{ .buf = cmd_buf, .len = sizeof(cmd_buf) },
146 		{ .buf = NULL, .len = buf_len }
147 	};
148 	const struct spi_buf_set tx = {
149 		.buffers = tx_buf, .count = ARRAY_SIZE(tx_buf)
150 	};
151 	struct spi_buf rx_buf[] = {
152 		{ .buf = NULL, .len = sizeof(cmd_buf) },
153 		{ .buf = buf_data, .len = buf_len }
154 	};
155 	const struct spi_buf_set rx = {
156 		.buffers = rx_buf, .count = ARRAY_SIZE(rx_buf)
157 	};
158 
159 	return spi_transceive_dt(&DEV_CFG(dev)->bus, &tx, &rx);
160 }
161 
162 /*
163  * Read RX Buffer instruction
164  *
165  * When reading a receive buffer, reduces the overhead of a normal READ
166  * command by placing the Address Pointer at one of four locations selected by
167  * parameter nm:
168  *   0: Receive Buffer 0, Start at RXB0SIDH (0x61)
169  *   1: Receive Buffer 0, Start at RXB0D0 (0x66)
170  *   2: Receive Buffer 1, Start at RXB1SIDH (0x71)
171  *   3: Receive Buffer 1, Start at RXB1D0 (0x76)
172  */
mcp2515_cmd_read_rx_buffer(const struct device * dev,uint8_t nm,uint8_t * buf_data,uint8_t buf_len)173 static int mcp2515_cmd_read_rx_buffer(const struct device *dev, uint8_t nm,
174 				      uint8_t *buf_data, uint8_t buf_len)
175 {
176 	__ASSERT(nm <= 0x03, "nm <= 0x03");
177 
178 	uint8_t cmd_buf[] = { MCP2515_OPCODE_READ_RX_BUFFER | (nm << 1) };
179 
180 	struct spi_buf tx_buf[] = {
181 		{ .buf = cmd_buf, .len = sizeof(cmd_buf) },
182 		{ .buf = NULL, .len = buf_len }
183 	};
184 	const struct spi_buf_set tx = {
185 		.buffers = tx_buf, .count = ARRAY_SIZE(tx_buf)
186 	};
187 	struct spi_buf rx_buf[] = {
188 		{ .buf = NULL, .len = sizeof(cmd_buf) },
189 		{ .buf = buf_data, .len = buf_len }
190 	};
191 	const struct spi_buf_set rx = {
192 		.buffers = rx_buf, .count = ARRAY_SIZE(rx_buf)
193 	};
194 
195 	return spi_transceive_dt(&DEV_CFG(dev)->bus, &tx, &rx);
196 }
197 
mcp2515_convert_canmode_to_mcp2515mode(enum can_mode mode)198 static uint8_t mcp2515_convert_canmode_to_mcp2515mode(enum can_mode mode)
199 {
200 	switch (mode) {
201 	case CAN_NORMAL_MODE:
202 		return MCP2515_MODE_NORMAL;
203 	case CAN_SILENT_MODE:
204 		return MCP2515_MODE_SILENT;
205 	case CAN_LOOPBACK_MODE:
206 		return MCP2515_MODE_LOOPBACK;
207 	default:
208 		LOG_ERR("Unsupported CAN Mode %u", mode);
209 		return MCP2515_MODE_SILENT;
210 	}
211 }
212 
mcp2515_convert_zcanframe_to_mcp2515frame(const struct zcan_frame * source,uint8_t * target)213 static void mcp2515_convert_zcanframe_to_mcp2515frame(const struct zcan_frame
214 						      *source, uint8_t *target)
215 {
216 	uint8_t rtr;
217 	uint8_t dlc;
218 	uint8_t data_idx = 0U;
219 
220 	if (source->id_type == CAN_STANDARD_IDENTIFIER) {
221 		target[MCP2515_FRAME_OFFSET_SIDH] = source->id >> 3;
222 		target[MCP2515_FRAME_OFFSET_SIDL] =
223 			(source->id & 0x07) << 5;
224 	} else {
225 		target[MCP2515_FRAME_OFFSET_SIDH] = source->id >> 21;
226 		target[MCP2515_FRAME_OFFSET_SIDL] =
227 			(((source->id >> 18) & 0x07) << 5) | (BIT(3)) |
228 			((source->id >> 16) & 0x03);
229 		target[MCP2515_FRAME_OFFSET_EID8] = source->id >> 8;
230 		target[MCP2515_FRAME_OFFSET_EID0] = source->id;
231 	}
232 
233 	rtr = (source->rtr == CAN_REMOTEREQUEST) ? BIT(6) : 0;
234 	dlc = (source->dlc) & 0x0F;
235 
236 	target[MCP2515_FRAME_OFFSET_DLC] = rtr | dlc;
237 
238 	for (; data_idx < CAN_MAX_DLC; data_idx++) {
239 		target[MCP2515_FRAME_OFFSET_D0 + data_idx] =
240 			source->data[data_idx];
241 	}
242 }
243 
mcp2515_convert_mcp2515frame_to_zcanframe(const uint8_t * source,struct zcan_frame * target)244 static void mcp2515_convert_mcp2515frame_to_zcanframe(const uint8_t *source,
245 						      struct zcan_frame *target)
246 {
247 	uint8_t data_idx = 0U;
248 
249 	if (source[MCP2515_FRAME_OFFSET_SIDL] & BIT(3)) {
250 		target->id_type = CAN_EXTENDED_IDENTIFIER;
251 		target->id =
252 			(source[MCP2515_FRAME_OFFSET_SIDH] << 21) |
253 			((source[MCP2515_FRAME_OFFSET_SIDL] >> 5) << 18) |
254 			((source[MCP2515_FRAME_OFFSET_SIDL] & 0x03) << 16) |
255 			(source[MCP2515_FRAME_OFFSET_EID8] << 8) |
256 			source[MCP2515_FRAME_OFFSET_EID0];
257 	} else {
258 		target->id_type = CAN_STANDARD_IDENTIFIER;
259 		target->id = (source[MCP2515_FRAME_OFFSET_SIDH] << 3) |
260 				 (source[MCP2515_FRAME_OFFSET_SIDL] >> 5);
261 	}
262 
263 	target->dlc = source[MCP2515_FRAME_OFFSET_DLC] & 0x0F;
264 	target->rtr = source[MCP2515_FRAME_OFFSET_DLC] & BIT(6) ?
265 		      CAN_REMOTEREQUEST : CAN_DATAFRAME;
266 
267 	for (; data_idx < CAN_MAX_DLC; data_idx++) {
268 		target->data[data_idx] = source[MCP2515_FRAME_OFFSET_D0 +
269 						data_idx];
270 	}
271 }
272 
mcp2515_set_mode_int(const struct device * dev,uint8_t mcp2515_mode)273 const int mcp2515_set_mode_int(const struct device *dev, uint8_t mcp2515_mode)
274 {
275 	uint8_t canstat;
276 
277 	mcp2515_cmd_bit_modify(dev, MCP2515_ADDR_CANCTRL,
278 			       MCP2515_CANCTRL_MODE_MASK,
279 			       mcp2515_mode << MCP2515_CANCTRL_MODE_POS);
280 	mcp2515_cmd_read_reg(dev, MCP2515_ADDR_CANSTAT, &canstat, 1);
281 
282 	if (((canstat & MCP2515_CANSTAT_MODE_MASK) >> MCP2515_CANSTAT_MODE_POS)
283 	    != mcp2515_mode) {
284 		LOG_ERR("Failed to set MCP2515 operation mode");
285 		return -EIO;
286 	}
287 
288 	return 0;
289 }
290 
mcp2515_get_mode(const struct device * dev,uint8_t * mode)291 static int mcp2515_get_mode(const struct device *dev, uint8_t *mode)
292 {
293 	uint8_t canstat;
294 
295 	if (mode == NULL) {
296 		return -EINVAL;
297 	}
298 
299 	if (mcp2515_cmd_read_reg(dev, MCP2515_ADDR_CANSTAT, &canstat, 1)) {
300 		return -EIO;
301 	}
302 
303 	*mode = (canstat & MCP2515_CANSTAT_MODE_MASK)
304 		>> MCP2515_CANSTAT_MODE_POS;
305 
306 	return 0;
307 }
308 
mcp2515_get_core_clock(const struct device * dev,uint32_t * rate)309 static int mcp2515_get_core_clock(const struct device *dev, uint32_t *rate)
310 {
311 	const struct mcp2515_config *dev_cfg = DEV_CFG(dev);
312 
313 	*rate = dev_cfg->osc_freq / 2;
314 	return 0;
315 }
316 
317 
mcp2515_set_timing(const struct device * dev,const struct can_timing * timing,const struct can_timing * timing_data)318 static int mcp2515_set_timing(const struct device *dev,
319 			      const struct can_timing *timing,
320 			      const struct can_timing *timing_data)
321 {
322 	ARG_UNUSED(timing_data);
323 	struct mcp2515_data *dev_data = DEV_DATA(dev);
324 	int ret;
325 
326 	if (!timing) {
327 		return -EINVAL;
328 	}
329 
330 	/* CNF3, CNF2, CNF1, CANINTE */
331 	uint8_t config_buf[4];
332 	uint8_t reset_mode;
333 
334 	/* CNF1; SJW<7:6> | BRP<5:0> */
335 	__ASSERT(timing->prescaler > 0, "Prescaler should be bigger than zero");
336 	uint8_t brp = timing->prescaler - 1;
337 	if (timing->sjw != CAN_SJW_NO_CHANGE) {
338 		dev_data->sjw = (timing->sjw - 1) << 6;
339 	}
340 
341 	uint8_t cnf1 = dev_data->sjw | brp;
342 
343 	/* CNF2; BTLMODE<7>|SAM<6>|PHSEG1<5:3>|PRSEG<2:0> */
344 	const uint8_t btlmode = 1 << 7;
345 	const uint8_t sam = 0 << 6;
346 	const uint8_t phseg1 = (timing->phase_seg1 - 1) << 3;
347 	const uint8_t prseg = (timing->prop_seg - 1);
348 
349 	const uint8_t cnf2 = btlmode | sam | phseg1 | prseg;
350 
351 	/* CNF3; SOF<7>|WAKFIL<6>|UND<5:3>|PHSEG2<2:0> */
352 	const uint8_t sof = 0 << 7;
353 	const uint8_t wakfil = 0 << 6;
354 	const uint8_t und = 0 << 3;
355 	const uint8_t phseg2 = (timing->phase_seg2 - 1);
356 
357 	const uint8_t cnf3 = sof | wakfil | und | phseg2;
358 
359 	const uint8_t caninte = MCP2515_INTE_RX0IE | MCP2515_INTE_RX1IE |
360 			     MCP2515_INTE_TX0IE | MCP2515_INTE_TX1IE |
361 			     MCP2515_INTE_TX2IE | MCP2515_INTE_ERRIE;
362 
363 	/* Receive everything, filtering done in driver, RXB0 roll over into
364 	 * RXB1 */
365 	const uint8_t rx0_ctrl = BIT(6) | BIT(5) | BIT(2);
366 	const uint8_t rx1_ctrl = BIT(6) | BIT(5);
367 
368 	__ASSERT(timing->sjw <= 4, "1 <= SJW <= 4");
369 	__ASSERT((timing->prop_seg >= 1) && (timing->prop_seg <= 8),
370 		 "1 <= PROP <= 8");
371 	__ASSERT((timing->phase_seg1 >= 1) && (timing->phase_seg1 <= 8),
372 		 "1 <= BS1 <= 8");
373 	__ASSERT((timing->phase_seg2 >= 2) && (timing->phase_seg2 <= 8),
374 		 "2 <= BS2 <= 8");
375 	__ASSERT(timing->prop_seg + timing->phase_seg1 >= timing->phase_seg2,
376 		 "PROP + BS1 >= BS2");
377 	__ASSERT(timing->phase_seg2 > timing->sjw, "BS2 > SJW");
378 
379 	config_buf[0] = cnf3;
380 	config_buf[1] = cnf2;
381 	config_buf[2] = cnf1;
382 	config_buf[3] = caninte;
383 
384 	k_mutex_lock(&dev_data->mutex, K_FOREVER);
385 
386 	k_usleep(MCP2515_OSC_STARTUP_US);
387 
388 	/* will enter configuration mode automatically */
389 	ret = mcp2515_cmd_soft_reset(dev);
390 	if (ret < 0) {
391 		LOG_ERR("Failed to reset the device [%d]", ret);
392 		goto done;
393 	}
394 
395 	k_usleep(MCP2515_OSC_STARTUP_US);
396 
397 	ret = mcp2515_get_mode(dev, &reset_mode);
398 	if (ret < 0) {
399 		LOG_ERR("Failed to read device mode [%d]",
400 			ret);
401 		goto done;
402 	}
403 
404 	if (reset_mode != MCP2515_MODE_CONFIGURATION) {
405 		LOG_ERR("Device did not reset into configuration mode [%d]",
406 			reset_mode);
407 		ret = -EIO;
408 		goto done;
409 	}
410 
411 	ret = mcp2515_cmd_write_reg(dev, MCP2515_ADDR_CNF3, config_buf,
412 				    sizeof(config_buf));
413 	if (ret < 0) {
414 		LOG_ERR("Failed to write the configuration [%d]", ret);
415 	}
416 
417 	ret = mcp2515_cmd_bit_modify(dev, MCP2515_ADDR_RXB0CTRL, rx0_ctrl,
418 				     rx0_ctrl);
419 	if (ret < 0) {
420 		LOG_ERR("Failed to write RXB0CTRL [%d]", ret);
421 	}
422 
423 	ret = mcp2515_cmd_bit_modify(dev, MCP2515_ADDR_RXB1CTRL, rx1_ctrl,
424 				     rx1_ctrl);
425 	if (ret < 0) {
426 		LOG_ERR("Failed to write RXB1CTRL [%d]", ret);
427 	}
428 
429 done:
430 	k_mutex_unlock(&dev_data->mutex);
431 	return ret;
432 }
433 
mcp2515_set_mode(const struct device * dev,enum can_mode mode)434 static int mcp2515_set_mode(const struct device *dev, enum can_mode mode)
435 {
436 	struct mcp2515_data *dev_data = DEV_DATA(dev);
437 	int ret;
438 
439 	k_mutex_lock(&dev_data->mutex, K_FOREVER);
440 	k_usleep(MCP2515_OSC_STARTUP_US);
441 
442 	ret = mcp2515_set_mode_int(dev,
443 			mcp2515_convert_canmode_to_mcp2515mode(mode));
444 	if (ret < 0) {
445 		LOG_ERR("Failed to set the mode [%d]", ret);
446 	}
447 
448 	k_mutex_unlock(&dev_data->mutex);
449 	return ret;
450 }
451 
mcp2515_send(const struct device * dev,const struct zcan_frame * msg,k_timeout_t timeout,can_tx_callback_t callback,void * callback_arg)452 static int mcp2515_send(const struct device *dev,
453 			const struct zcan_frame *msg,
454 			k_timeout_t timeout, can_tx_callback_t callback,
455 			void *callback_arg)
456 {
457 	struct mcp2515_data *dev_data = DEV_DATA(dev);
458 	uint8_t tx_idx = 0U;
459 	uint8_t abc;
460 	uint8_t nnn;
461 	uint8_t len;
462 	uint8_t tx_frame[MCP2515_FRAME_LEN];
463 
464 	if (msg->dlc > CAN_MAX_DLC) {
465 		LOG_ERR("DLC of %d exceeds maximum (%d)",
466 			msg->dlc, CAN_MAX_DLC);
467 		return CAN_TX_EINVAL;
468 	}
469 
470 	if (k_sem_take(&dev_data->tx_sem, timeout) != 0) {
471 		return CAN_TIMEOUT;
472 	}
473 
474 	k_mutex_lock(&dev_data->mutex, K_FOREVER);
475 
476 	/* find a free tx slot */
477 	for (; tx_idx < MCP2515_TX_CNT; tx_idx++) {
478 		if ((BIT(tx_idx) & dev_data->tx_busy_map) == 0) {
479 			dev_data->tx_busy_map |= BIT(tx_idx);
480 			break;
481 		}
482 	}
483 
484 	k_mutex_unlock(&dev_data->mutex);
485 
486 	if (tx_idx == MCP2515_TX_CNT) {
487 		LOG_WRN("no free tx slot available");
488 		return CAN_TX_ERR;
489 	}
490 
491 	dev_data->tx_cb[tx_idx].cb = callback;
492 	dev_data->tx_cb[tx_idx].cb_arg = callback_arg;
493 
494 	mcp2515_convert_zcanframe_to_mcp2515frame(msg, tx_frame);
495 
496 	/* Address Pointer selection */
497 	abc = 2 * tx_idx;
498 
499 	/* Calculate minimum length to transfer */
500 	len = sizeof(tx_frame) - CAN_MAX_DLC + msg->dlc;
501 
502 	mcp2515_cmd_load_tx_buffer(dev, abc, tx_frame, len);
503 
504 	/* request tx slot transmission */
505 	nnn = BIT(tx_idx);
506 	mcp2515_cmd_rts(dev, nnn);
507 
508 	if (callback == NULL) {
509 		k_sem_take(&dev_data->tx_cb[tx_idx].sem, K_FOREVER);
510 	}
511 
512 	return 0;
513 }
514 
mcp2515_attach_isr(const struct device * dev,can_rx_callback_t rx_cb,void * cb_arg,const struct zcan_filter * filter)515 static int mcp2515_attach_isr(const struct device *dev,
516 			      can_rx_callback_t rx_cb,
517 			      void *cb_arg,
518 			      const struct zcan_filter *filter)
519 {
520 	struct mcp2515_data *dev_data = DEV_DATA(dev);
521 	int filter_idx = 0;
522 
523 	__ASSERT(rx_cb != NULL, "response_ptr can not be null");
524 
525 	k_mutex_lock(&dev_data->mutex, K_FOREVER);
526 
527 	/* find free filter */
528 	while ((BIT(filter_idx) & dev_data->filter_usage)
529 	       && (filter_idx < CONFIG_CAN_MAX_FILTER)) {
530 		filter_idx++;
531 	}
532 
533 	/* setup filter */
534 	if (filter_idx < CONFIG_CAN_MAX_FILTER) {
535 		dev_data->filter_usage |= BIT(filter_idx);
536 
537 		dev_data->filter[filter_idx] = *filter;
538 		dev_data->rx_cb[filter_idx] = rx_cb;
539 		dev_data->cb_arg[filter_idx] = cb_arg;
540 
541 	} else {
542 		filter_idx = CAN_NO_FREE_FILTER;
543 	}
544 
545 	k_mutex_unlock(&dev_data->mutex);
546 
547 	return filter_idx;
548 }
549 
mcp2515_detach(const struct device * dev,int filter_nr)550 static void mcp2515_detach(const struct device *dev, int filter_nr)
551 {
552 	struct mcp2515_data *dev_data = DEV_DATA(dev);
553 
554 	if (filter_nr < 0 || filter_nr >= CONFIG_CAN_MAX_FILTER) {
555 		LOG_ERR("filter ID %d out of bounds", filter_nr);
556 		return;
557 	}
558 
559 	k_mutex_lock(&dev_data->mutex, K_FOREVER);
560 	dev_data->filter_usage &= ~BIT(filter_nr);
561 	k_mutex_unlock(&dev_data->mutex);
562 }
563 
mcp2515_register_state_change_isr(const struct device * dev,can_state_change_isr_t isr)564 static void mcp2515_register_state_change_isr(const struct device *dev,
565 						can_state_change_isr_t isr)
566 {
567 	struct mcp2515_data *dev_data = DEV_DATA(dev);
568 
569 	dev_data->state_change_isr = isr;
570 }
571 
mcp2515_rx_filter(const struct device * dev,struct zcan_frame * msg)572 static void mcp2515_rx_filter(const struct device *dev,
573 			      struct zcan_frame *msg)
574 {
575 	struct mcp2515_data *dev_data = DEV_DATA(dev);
576 	uint8_t filter_idx = 0U;
577 	can_rx_callback_t callback;
578 	struct zcan_frame tmp_msg;
579 
580 	k_mutex_lock(&dev_data->mutex, K_FOREVER);
581 
582 	for (; filter_idx < CONFIG_CAN_MAX_FILTER; filter_idx++) {
583 		if (!(BIT(filter_idx) & dev_data->filter_usage)) {
584 			continue; /* filter slot empty */
585 		}
586 
587 		if (!can_utils_filter_match(msg,
588 					    &dev_data->filter[filter_idx])) {
589 			continue; /* filter did not match */
590 		}
591 
592 		callback = dev_data->rx_cb[filter_idx];
593 		/*Make a temporary copy in case the user modifies the message*/
594 		tmp_msg = *msg;
595 
596 		callback(&tmp_msg, dev_data->cb_arg[filter_idx]);
597 	}
598 
599 	k_mutex_unlock(&dev_data->mutex);
600 }
601 
mcp2515_rx(const struct device * dev,uint8_t rx_idx)602 static void mcp2515_rx(const struct device *dev, uint8_t rx_idx)
603 {
604 	__ASSERT(rx_idx < MCP2515_RX_CNT, "rx_idx < MCP2515_RX_CNT");
605 
606 	struct zcan_frame msg;
607 	uint8_t rx_frame[MCP2515_FRAME_LEN];
608 	uint8_t nm;
609 
610 	/* Address Pointer selection */
611 	nm = 2 * rx_idx;
612 
613 	/* Fetch rx buffer */
614 	mcp2515_cmd_read_rx_buffer(dev, nm, rx_frame, sizeof(rx_frame));
615 	mcp2515_convert_mcp2515frame_to_zcanframe(rx_frame, &msg);
616 	mcp2515_rx_filter(dev, &msg);
617 }
618 
mcp2515_tx_done(const struct device * dev,uint8_t tx_idx)619 static void mcp2515_tx_done(const struct device *dev, uint8_t tx_idx)
620 {
621 	struct mcp2515_data *dev_data = DEV_DATA(dev);
622 
623 	if (dev_data->tx_cb[tx_idx].cb == NULL) {
624 		k_sem_give(&dev_data->tx_cb[tx_idx].sem);
625 	} else {
626 		dev_data->tx_cb[tx_idx].cb(0, dev_data->tx_cb[tx_idx].cb_arg);
627 	}
628 
629 	k_mutex_lock(&dev_data->mutex, K_FOREVER);
630 	dev_data->tx_busy_map &= ~BIT(tx_idx);
631 	k_mutex_unlock(&dev_data->mutex);
632 	k_sem_give(&dev_data->tx_sem);
633 }
634 
mcp2515_get_state(const struct device * dev,struct can_bus_err_cnt * err_cnt)635 static enum can_state mcp2515_get_state(const struct device *dev,
636 					struct can_bus_err_cnt *err_cnt)
637 {
638 	uint8_t eflg;
639 	uint8_t err_cnt_buf[2];
640 	int ret;
641 
642 	ret = mcp2515_cmd_read_reg(dev, MCP2515_ADDR_EFLG, &eflg, sizeof(eflg));
643 	if (ret < 0) {
644 		LOG_ERR("Failed to read error register [%d]", ret);
645 		return CAN_BUS_UNKNOWN;
646 	}
647 
648 	if (err_cnt) {
649 		ret = mcp2515_cmd_read_reg(dev, MCP2515_ADDR_TEC, err_cnt_buf,
650 					   sizeof(err_cnt_buf));
651 		if (ret < 0) {
652 			LOG_ERR("Failed to read error counters [%d]", ret);
653 			return CAN_BUS_UNKNOWN;
654 		}
655 
656 		err_cnt->tx_err_cnt = err_cnt_buf[0];
657 		err_cnt->rx_err_cnt = err_cnt_buf[1];
658 	}
659 
660 	if (eflg & MCP2515_EFLG_TXBO) {
661 		return CAN_BUS_OFF;
662 	}
663 
664 	if ((eflg & MCP2515_EFLG_RXEP) || (eflg & MCP2515_EFLG_TXEP)) {
665 		return CAN_ERROR_PASSIVE;
666 	}
667 
668 	return CAN_ERROR_ACTIVE;
669 }
670 
mcp2515_handle_errors(const struct device * dev)671 static void mcp2515_handle_errors(const struct device *dev)
672 {
673 	struct mcp2515_data *dev_data = DEV_DATA(dev);
674 	can_state_change_isr_t state_change_isr = dev_data->state_change_isr;
675 	enum can_state state;
676 	struct can_bus_err_cnt err_cnt;
677 
678 	state = mcp2515_get_state(dev, state_change_isr ? &err_cnt : NULL);
679 
680 	if (state_change_isr && dev_data->old_state != state) {
681 		dev_data->old_state = state;
682 		state_change_isr(state, err_cnt);
683 	}
684 }
685 
686 #ifndef CONFIG_CAN_AUTO_BUS_OFF_RECOVERY
mcp2515_recover(const struct device * dev,k_timeout_t timeout)687 static void mcp2515_recover(const struct device *dev, k_timeout_t timeout)
688 {
689 	ARG_UNUSED(dev);
690 	ARG_UNUSED(timeout);
691 }
692 #endif
693 
mcp2515_handle_interrupts(const struct device * dev)694 static void mcp2515_handle_interrupts(const struct device *dev)
695 {
696 	const struct mcp2515_config *dev_cfg = DEV_CFG(dev);
697 	struct mcp2515_data *dev_data = DEV_DATA(dev);
698 	int ret;
699 	uint8_t canintf;
700 
701 	/* Loop until INT pin is inactive (all interrupt flags handled) */
702 	while (1) {
703 		ret = mcp2515_cmd_read_reg(dev, MCP2515_ADDR_CANINTF,
704 				&canintf, 1);
705 		if (ret != 0) {
706 			LOG_ERR("Couldn't read INTF register %d", ret);
707 			continue;
708 		}
709 
710 		if (canintf == 0) {
711 			/* No interrupt flags set */
712 			break;
713 		}
714 
715 		if (canintf & MCP2515_CANINTF_RX0IF) {
716 			mcp2515_rx(dev, 0);
717 
718 			/* RX0IF flag cleared automatically during read */
719 			canintf &= ~MCP2515_CANINTF_RX0IF;
720 		}
721 
722 		if (canintf & MCP2515_CANINTF_RX1IF) {
723 			mcp2515_rx(dev, 1);
724 
725 			/* RX1IF flag cleared automatically during read */
726 			canintf &= ~MCP2515_CANINTF_RX1IF;
727 		}
728 
729 		if (canintf & MCP2515_CANINTF_TX0IF) {
730 			mcp2515_tx_done(dev, 0);
731 		}
732 
733 		if (canintf & MCP2515_CANINTF_TX1IF) {
734 			mcp2515_tx_done(dev, 1);
735 		}
736 
737 		if (canintf & MCP2515_CANINTF_TX2IF) {
738 			mcp2515_tx_done(dev, 2);
739 		}
740 
741 		if (canintf & MCP2515_CANINTF_ERRIF) {
742 			mcp2515_handle_errors(dev);
743 		}
744 
745 		if (canintf != 0) {
746 			/* Clear remaining flags */
747 			mcp2515_cmd_bit_modify(dev, MCP2515_ADDR_CANINTF,
748 					canintf, ~canintf);
749 		}
750 
751 		/* Break from loop if INT pin is inactive */
752 		ret = gpio_pin_get(dev_data->int_gpio, dev_cfg->int_pin);
753 		if (ret < 0) {
754 			LOG_ERR("Couldn't read INT pin");
755 		} else if (ret == 0) {
756 			/* All interrupt flags handled */
757 			break;
758 		}
759 	}
760 }
761 
mcp2515_int_thread(const struct device * dev)762 static void mcp2515_int_thread(const struct device *dev)
763 {
764 	struct mcp2515_data *dev_data = DEV_DATA(dev);
765 
766 	while (1) {
767 		k_sem_take(&dev_data->int_sem, K_FOREVER);
768 		mcp2515_handle_interrupts(dev);
769 	}
770 }
771 
mcp2515_int_gpio_callback(const struct device * dev,struct gpio_callback * cb,uint32_t pins)772 static void mcp2515_int_gpio_callback(const struct device *dev,
773 				      struct gpio_callback *cb, uint32_t pins)
774 {
775 	struct mcp2515_data *dev_data =
776 		CONTAINER_OF(cb, struct mcp2515_data, int_gpio_cb);
777 
778 	k_sem_give(&dev_data->int_sem);
779 }
780 
781 static const struct can_driver_api can_api_funcs = {
782 	.set_timing = mcp2515_set_timing,
783 	.set_mode = mcp2515_set_mode,
784 	.send = mcp2515_send,
785 	.attach_isr = mcp2515_attach_isr,
786 	.detach = mcp2515_detach,
787 	.get_state = mcp2515_get_state,
788 #ifndef CONFIG_CAN_AUTO_BUS_OFF_RECOVERY
789 	.recover = mcp2515_recover,
790 #endif
791 	.register_state_change_isr = mcp2515_register_state_change_isr,
792 	.get_core_clock = mcp2515_get_core_clock,
793 	.timing_min = {
794 		.sjw = 0x1,
795 		.prop_seg = 0x01,
796 		.phase_seg1 = 0x01,
797 		.phase_seg2 = 0x01,
798 		.prescaler = 0x01
799 	},
800 	.timing_max = {
801 		.sjw = 0x04,
802 		.prop_seg = 0x08,
803 		.phase_seg1 = 0x08,
804 		.phase_seg2 = 0x08,
805 		.prescaler = 0x20
806 	}
807 };
808 
809 
mcp2515_init(const struct device * dev)810 static int mcp2515_init(const struct device *dev)
811 {
812 	const struct mcp2515_config *dev_cfg = DEV_CFG(dev);
813 	struct mcp2515_data *dev_data = DEV_DATA(dev);
814 	int ret;
815 	struct can_timing timing;
816 
817 	k_sem_init(&dev_data->int_sem, 0, 1);
818 	k_mutex_init(&dev_data->mutex);
819 	k_sem_init(&dev_data->tx_sem, MCP2515_TX_CNT, MCP2515_TX_CNT);
820 	k_sem_init(&dev_data->tx_cb[0].sem, 0, 1);
821 	k_sem_init(&dev_data->tx_cb[1].sem, 0, 1);
822 	k_sem_init(&dev_data->tx_cb[2].sem, 0, 1);
823 
824 	if (!spi_is_ready(&dev_cfg->bus)) {
825 		LOG_ERR("SPI bus %s not ready", dev_cfg->bus.bus->name);
826 		return -ENODEV;
827 	}
828 
829 	/* Reset MCP2515 */
830 	if (mcp2515_cmd_soft_reset(dev)) {
831 		LOG_ERR("Soft-reset failed");
832 		return -EIO;
833 	}
834 
835 	/* Initialize interrupt handling  */
836 	dev_data->int_gpio = device_get_binding(dev_cfg->int_port);
837 	if (dev_data->int_gpio == NULL) {
838 		LOG_ERR("GPIO port %s not found", dev_cfg->int_port);
839 		return -EINVAL;
840 	}
841 
842 	if (gpio_pin_configure(dev_data->int_gpio, dev_cfg->int_pin,
843 			       (GPIO_INPUT |
844 				DT_INST_GPIO_FLAGS(0, int_gpios)))) {
845 		LOG_ERR("Unable to configure GPIO pin %u", dev_cfg->int_pin);
846 		return -EINVAL;
847 	}
848 
849 	gpio_init_callback(&(dev_data->int_gpio_cb), mcp2515_int_gpio_callback,
850 			   BIT(dev_cfg->int_pin));
851 
852 	if (gpio_add_callback(dev_data->int_gpio, &(dev_data->int_gpio_cb))) {
853 		return -EINVAL;
854 	}
855 
856 	if (gpio_pin_interrupt_configure(dev_data->int_gpio, dev_cfg->int_pin,
857 					 GPIO_INT_EDGE_TO_ACTIVE)) {
858 		return -EINVAL;
859 	}
860 
861 	k_thread_create(&dev_data->int_thread, dev_data->int_thread_stack,
862 			dev_cfg->int_thread_stack_size,
863 			(k_thread_entry_t) mcp2515_int_thread, (void *)dev,
864 			NULL, NULL, K_PRIO_COOP(dev_cfg->int_thread_priority),
865 			0, K_NO_WAIT);
866 
867 	(void)memset(dev_data->rx_cb, 0, sizeof(dev_data->rx_cb));
868 	(void)memset(dev_data->filter, 0, sizeof(dev_data->filter));
869 	dev_data->old_state = CAN_ERROR_ACTIVE;
870 
871 	timing.sjw = dev_cfg->tq_sjw;
872 	if (dev_cfg->sample_point && USE_SP_ALGO) {
873 		ret = can_calc_timing(dev, &timing, dev_cfg->bus_speed,
874 				      dev_cfg->sample_point);
875 		if (ret == -EINVAL) {
876 			LOG_ERR("Can't find timing for given param");
877 			return -EIO;
878 		}
879 		LOG_DBG("Presc: %d, BS1: %d, BS2: %d",
880 			timing.prescaler, timing.phase_seg1, timing.phase_seg2);
881 		LOG_DBG("Sample-point err : %d", ret);
882 	} else {
883 		timing.prop_seg = dev_cfg->tq_prop;
884 		timing.phase_seg1 = dev_cfg->tq_bs1;
885 		timing.phase_seg2 = dev_cfg->tq_bs2;
886 		ret = can_calc_prescaler(dev, &timing, dev_cfg->bus_speed);
887 		if (ret) {
888 			LOG_WRN("Bitrate error: %d", ret);
889 		}
890 	}
891 
892 	ret = can_set_timing(dev, &timing, NULL);
893 	if (ret) {
894 		return ret;
895 	}
896 
897 	ret = can_set_mode(dev, CAN_NORMAL_MODE);
898 
899 	return ret;
900 }
901 
902 #if DT_NODE_HAS_STATUS(DT_DRV_INST(0), okay)
903 
904 static K_KERNEL_STACK_DEFINE(mcp2515_int_thread_stack,
905 			     CONFIG_CAN_MCP2515_INT_THREAD_STACK_SIZE);
906 
907 static struct mcp2515_data mcp2515_data_1 = {
908 	.int_thread_stack = mcp2515_int_thread_stack,
909 	.tx_cb[0].cb = NULL,
910 	.tx_cb[1].cb = NULL,
911 	.tx_cb[2].cb = NULL,
912 	.tx_busy_map = 0U,
913 	.filter_usage = 0U,
914 };
915 
916 static const struct mcp2515_config mcp2515_config_1 = {
917 	.bus = SPI_DT_SPEC_INST_GET(0, SPI_WORD_SET(8), 0),
918 	.int_pin = DT_INST_GPIO_PIN(0, int_gpios),
919 	.int_port = DT_INST_GPIO_LABEL(0, int_gpios),
920 	.int_thread_stack_size = CONFIG_CAN_MCP2515_INT_THREAD_STACK_SIZE,
921 	.int_thread_priority = CONFIG_CAN_MCP2515_INT_THREAD_PRIO,
922 	.tq_sjw = DT_INST_PROP(0, sjw),
923 	.tq_prop = DT_INST_PROP_OR(0, prop_seg, 0),
924 	.tq_bs1 = DT_INST_PROP_OR(0, phase_seg1, 0),
925 	.tq_bs2 = DT_INST_PROP_OR(0, phase_seg2, 0),
926 	.bus_speed = DT_INST_PROP(0, bus_speed),
927 	.osc_freq = DT_INST_PROP(0, osc_freq),
928 	.sample_point = DT_INST_PROP_OR(0, sample_point, 0)
929 };
930 
931 DEVICE_DT_INST_DEFINE(0, &mcp2515_init, NULL,
932 		    &mcp2515_data_1, &mcp2515_config_1, POST_KERNEL,
933 		    CONFIG_CAN_MCP2515_INIT_PRIORITY, &can_api_funcs);
934 
935 #if defined(CONFIG_NET_SOCKETS_CAN)
936 
937 #include "socket_can_generic.h"
938 
939 static struct socket_can_context socket_can_context_1;
940 
socket_can_init(const struct device * dev)941 static int socket_can_init(const struct device *dev)
942 {
943 	const struct device *can_dev = DEVICE_DT_INST_GET(1);
944 	struct socket_can_context *socket_context = dev->data;
945 
946 	LOG_DBG("Init socket CAN device %p (%s) for dev %p (%s)",
947 		dev, dev->name, can_dev, can_dev->name);
948 
949 	socket_context->can_dev = can_dev;
950 	socket_context->msgq = &socket_can_msgq;
951 
952 	socket_context->rx_tid =
953 		k_thread_create(&socket_context->rx_thread_data,
954 				rx_thread_stack,
955 				K_KERNEL_STACK_SIZEOF(rx_thread_stack),
956 				rx_thread, socket_context, NULL, NULL,
957 				RX_THREAD_PRIORITY, 0, K_NO_WAIT);
958 
959 	return 0;
960 }
961 
962 NET_DEVICE_INIT(socket_can_mcp2515_1, SOCKET_CAN_NAME_1, socket_can_init,
963 		NULL, &socket_can_context_1, NULL,
964 		CONFIG_KERNEL_INIT_PRIORITY_DEVICE,
965 		&socket_can_api,
966 		CANBUS_RAW_L2, NET_L2_GET_CTX_TYPE(CANBUS_RAW_L2), CAN_MTU);
967 
968 #endif
969 
970 #endif /* DT_NODE_HAS_STATUS(DT_DRV_INST(0), okay) */
971