Skip to content

Commit d6fc3f6

Browse files
henrikbrixandersenfabiobaltieri
authored andcommitted
drivers: can: provide default callback to can_send() if NULL
Provide a default, internal callback to CAN controller drivers implementation of can_send() if no callback was provided by the caller. This allows for simplifying the CAN driver implementations of can_send() as these no longer need special handling for callback/no callback operation. Signed-off-by: Henrik Brix Andersen <[email protected]>
1 parent 97feeb4 commit d6fc3f6

File tree

2 files changed

+41
-9
lines changed

2 files changed

+41
-9
lines changed

drivers/can/can_common.c

Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,44 @@ LOG_MODULE_REGISTER(can_common, CONFIG_CAN_LOG_LEVEL);
1717
/* CAN sync segment is always one time quantum */
1818
#define CAN_SYNC_SEG 1
1919

20+
struct can_tx_default_cb_ctx {
21+
struct k_sem done;
22+
int status;
23+
};
24+
25+
static void can_tx_default_cb(const struct device *dev, int error, void *user_data)
26+
{
27+
struct can_tx_default_cb_ctx *ctx = user_data;
28+
29+
ctx->status = error;
30+
k_sem_give(&ctx->done);
31+
}
32+
33+
int z_impl_can_send(const struct device *dev, const struct can_frame *frame,
34+
k_timeout_t timeout, can_tx_callback_t callback,
35+
void *user_data)
36+
{
37+
const struct can_driver_api *api = (const struct can_driver_api *)dev->api;
38+
39+
if (callback == NULL) {
40+
struct can_tx_default_cb_ctx ctx;
41+
int err;
42+
43+
k_sem_init(&ctx.done, 0, 1);
44+
45+
err = api->send(dev, frame, timeout, can_tx_default_cb, &ctx);
46+
if (err != 0) {
47+
return err;
48+
}
49+
50+
k_sem_take(&ctx.done, K_FOREVER);
51+
52+
return ctx.status;
53+
}
54+
55+
return api->send(dev, frame, timeout, callback, user_data);
56+
}
57+
2058
static void can_msgq_put(const struct device *dev, struct can_frame *frame, void *user_data)
2159
{
2260
struct k_msgq *msgq = (struct k_msgq *)user_data;

include/zephyr/drivers/can.h

Lines changed: 3 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -348,6 +348,9 @@ typedef int (*can_set_mode_t)(const struct device *dev, can_mode_t mode);
348348
/**
349349
* @brief Callback API upon sending a CAN frame
350350
* See @a can_send() for argument description
351+
*
352+
* @note From a driver perspective `callback` will never be `NULL` as a default callback will be
353+
* provided if none is provided by the caller. This allows for simplifying the driver handling.
351354
*/
352355
typedef int (*can_send_t)(const struct device *dev,
353356
const struct can_frame *frame,
@@ -1095,15 +1098,6 @@ __syscall int can_send(const struct device *dev, const struct can_frame *frame,
10951098
k_timeout_t timeout, can_tx_callback_t callback,
10961099
void *user_data);
10971100

1098-
static inline int z_impl_can_send(const struct device *dev, const struct can_frame *frame,
1099-
k_timeout_t timeout, can_tx_callback_t callback,
1100-
void *user_data)
1101-
{
1102-
const struct can_driver_api *api = (const struct can_driver_api *)dev->api;
1103-
1104-
return api->send(dev, frame, timeout, callback, user_data);
1105-
}
1106-
11071101
/** @} */
11081102

11091103
/**

0 commit comments

Comments
 (0)