24 #ifndef LELY_IO2_CAN_HPP_ 25 #define LELY_IO2_CAN_HPP_ 49 NONE = IO_CAN_BUS_FLAG_NONE,
50 MASK = IO_CAN_BUS_FLAG_MASK
55 return static_cast<CanBusFlag>(~static_cast<
int>(rhs));
59 return static_cast<CanBusFlag>(
static_cast<int>(lhs) & static_cast<int>(rhs));
64 return static_cast<CanBusFlag>(
static_cast<int>(lhs) ^ static_cast<int>(rhs));
69 return static_cast<CanBusFlag>(
static_cast<int>(lhs) | static_cast<int>(rhs));
74 return lhs = lhs & rhs;
79 return lhs = lhs ^ rhs;
84 return lhs = lhs | rhs;
93 ::std::chrono::nanoseconds* dp,
ev_exec_t* exec, F&& f)
95 msg, err, dp ? &ts_ :
nullptr, exec,
98 auto result = read->r.result;
102 if (self->dp_) *
self->dp_ = util::from_timespec(self->ts_);
103 compat::invoke(::std::move(self->func_), result, ec);
107 func_(::std::forward<F>(f)) {}
113 operator ev_task&() & noexcept {
return task; }
117 ::std::chrono::nanoseconds* dp_{
nullptr};
118 typename ::std::decay<F>::type func_;
129 inline typename ::std::enable_if<
133 ::std::chrono::nanoseconds* dp,
ev_exec_t* exec,
136 ::std::forward<F>(f));
146 using Signature = void(
int, ::std::error_code);
158 *
self->dp_ = util::from_timespec(self->ts_);
160 auto result = read->r.result;
161 ::std::error_code ec;
164 self->func_(result, ec);
168 func_(::std::forward<F>(f)) {}
180 operator ev_task&() & noexcept {
return task; }
190 ::std::chrono::nanoseconds* dp_{
nullptr};
191 ::std::function<Signature> func_;
206 compat::invoke(::std::move(self->func_), ec);
209 func_(::std::forward<F>(f)) {}
216 typename ::std::decay<F>::type func_;
228 inline typename ::std::enable_if<
243 using Signature = void(::std::error_code);
258 func_(::std::forward<F>(f)) {}
269 operator ev_task&() & noexcept {
return task; }
278 ::std::function<Signature> func_;
293 stop(::std::error_code& ec) noexcept {
306 ::std::error_code ec;
308 if (ec) throw ::std::system_error(ec,
"stop");
313 stopped(::std::error_code& ec)
const noexcept {
330 ::std::error_code ec;
331 auto result = stopped(ec);
332 if (ec) throw ::std::system_error(ec,
"stopped");
351 ::std::error_code ec;
353 if (ec) throw ::std::system_error(ec,
"restart");
358 get_bitrate(
int* pnominal,
int* pdata, ::std::error_code& ec)
const noexcept {
371 ::std::error_code ec;
372 get_bitrate(pnominal, pdata, ec);
373 if (ec) throw ::std::system_error(ec,
"get_bitrate");
378 set_bitrate(
int nominal,
int data, ::std::error_code& ec) noexcept {
391 ::std::error_code ec;
392 set_bitrate(nominal, data, ec);
393 if (ec) throw ::std::system_error(ec,
"set_bitrate");
409 return static_cast<CanState>(state);
415 ::std::error_code ec;
416 auto result = get_state(ec);
417 if (ec) throw ::std::system_error(ec,
"get_state");
442 if (flags == -1) util::throw_errc(
"get_flags");
449 ::std::error_code& ec) noexcept {
452 timespec ts = {0, 0};
453 int result =
io_can_chan_read(*
this, msg, err, dp ? &ts :
nullptr, timeout);
458 if (dp) *dp = util::from_timespec(ts);
466 ::std::chrono::nanoseconds* dp =
nullptr,
int timeout = -1) {
467 ::std::error_code ec;
468 int result = read(msg, err, dp, timeout, ec);
469 if (result < 0) throw ::std::system_error(ec,
"read");
485 ::std::forward<F>(f)));
493 submit_read(msg, err, dp,
nullptr, ::std::forward<F>(f));
511 timespec* tp =
nullptr,
521 return async_read(
nullptr, msg, err, tp, pread);
526 write(
const can_msg& msg,
int timeout, ::std::error_code& ec) noexcept {
539 ::std::error_code ec;
540 write(msg, timeout, ec);
541 if (ec) throw ::std::system_error(ec,
"write");
562 submit_write(msg,
nullptr, ::std::forward<F>(f));
582 if (!future) util::throw_errc(
"async_write");
589 return async_write(
nullptr, msg, pwrite);
599 #endif // !LELY_IO2_CAN_HPP_
void set_bitrate(int nominal, int data, ::std::error_code &ec) noexcept
A CAN or CAN FD format frame.
const struct ev_exec_vtbl *const ev_exec_t
An abstract task executor.
A CAN channel read operation.
void stop(::std::error_code &ec) noexcept
CanChannelRead(can_msg *msg, can_err *err, ::std::chrono::nanoseconds *dp, ev_exec_t *exec, F &&f)
Constructs a read operation with a completion task.
ev_future_t * io_can_chan_async_write(io_can_chan_t *chan, ev_exec_t *exec, const struct can_msg *msg, struct io_can_chan_write **pwrite)
Submits an asynchronous write operation to a CAN channel and creates a future which becomes ready onc...
CanBusFlag get_flags() const
static size_t io_can_chan_cancel_write(io_can_chan_t *chan, struct io_can_chan_write *write)
Cancels the specified CAN channel write operation if it is pending.
Determines whether F can be invoked with the arguments Args....
CanChannelWrite(const can_msg &msg, F &&f)
Constructs a write operation with a completion task.
int io_can_chan_write(io_can_chan_t *chan, const struct can_msg *msg, int timeout)
Writes a CAN frame to a CAN channel.
void submit_read(struct io_can_chan_read &read) noexcept
void submit_read(can_msg *msg, can_err *err, ::std::chrono::nanoseconds *dp, F &&f)
ev::Executor get_executor() const noexcept
Returns the executor to which the completion task is (to be) submitted.
bool stopped(::std::error_code &ec) const noexcept
CanState
The states of a CAN node, depending on the TX/RX error count.
bool abort_write(struct io_can_chan_write &write) noexcept
CanBusFlag
The CAN bus flags.
int io_can_ctrl_stop(io_can_ctrl_t *ctrl)
Stops a CAN controller.
ev::Executor get_executor() const noexcept
Returns the executor to which the completion task is (to be) submitted.
void set_bitrate(int nominal, int data=0)
A read operation suitable for use with a CAN channel.
void write(const can_msg &msg, int timeout, ::std::error_code &ec) noexcept
#define IO_CAN_CHAN_READ_INIT(msg, err, tp, exec, func)
The static initializer for io_can_chan_read.
int io_can_ctrl_stopped(const io_can_ctrl_t *ctrl)
Returns 1 in the CAN controller is stopped, 0 if not, and -1 on error.
CanChannelWrite(const can_msg &msg, ev_exec_t *exec, F &&f)
Constructs a write operation with a completion task.
void set_errc(int errc)
Sets the current (thread-specific) native error code to errc.
FD Format (formerly Extended Data Length) support is enabled.
A CAN channel write operation.
Bit Rate Switch support is enabled.
void restart(::std::error_code &ec) noexcept
const struct io_can_chan_vtbl *const io_can_chan_t
An abstract CAN channel.
void io_can_chan_submit_read(io_can_chan_t *chan, struct io_can_chan_read *read)
Submits a read operation to a CAN channel.
int io_can_chan_read(io_can_chan_t *chan, struct can_msg *msg, struct can_err *err, struct timespec *tp, int timeout)
Reads a CAN frame or CAN error frame from a CAN channel.
void get_bitrate(int *pnominal, int *pdata, ::std::error_code &ec) const noexcept
ev::Future< void, int > async_write(ev_exec_t *exec, const can_msg &msg, struct io_can_chan_write **pwrite=nullptr)
static size_t io_can_chan_cancel_read(io_can_chan_t *chan, struct io_can_chan_read *read)
Cancels the specified CAN channel read operation if it is pending.
bool cancel_read(struct io_can_chan_read &read) noexcept
static size_t io_can_chan_abort_read(io_can_chan_t *chan, struct io_can_chan_read *read)
Aborts the specified CAN channel read operation if it is pending.
ev_future_t * io_can_chan_async_read(io_can_chan_t *chan, ev_exec_t *exec, struct can_msg *msg, struct can_err *err, struct timespec *tp, struct io_can_chan_read **pread)
Submits an asynchronous read operation to a CAN channel and creates a future which becomes ready once...
void submit_write(const can_msg &msg, ev_exec_t *exec, F &&f)
struct io_can_chan_read * io_can_chan_read_from_task(struct ev_task *task)
Obtains a pointer to a CAN channel read operation from a pointer to its completion task...
int get_errc(void)
Returns the last (thread-specific) native error code set by a system call or library function...
CanState get_state(::std::error_code &ec) const noexcept
ev::Future< int, int > async_read(ev_exec_t *exec, can_msg *msg, can_err *err=nullptr, timespec *tp=nullptr, struct io_can_chan_read **pread=nullptr)
io_dev_t * io_can_chan_get_dev(const io_can_chan_t *chan)
Returns a pointer to the abstract I/O device representing the CAN channel.
ev::Future< int, int > async_read(can_msg *msg, can_err *err=nullptr, timespec *tp=nullptr, struct io_can_chan_read **pread=nullptr)
void get_bitrate(int *pnominal, int *pdata=nullptr) const
void submit_write(struct io_can_chan_write &write) noexcept
A write operation suitable for use with a CAN channel.
bool cancel_write(struct io_can_chan_write &write) noexcept
typename ::std::enable_if< compat::is_invocable< F, ::std::error_code >::value, detail::CanChannelWriteWrapper< F > * >::type make_can_channel_write_wrapper(const can_msg &msg, ev_exec_t *exec, F &&f)
Creates a CAN channel write operation with a completion task.
This header file is part of the event library; it contains the C++ interface for the futures and prom...
Reception of error frames is enabled.
CanChannelRead(can_msg *msg, can_err *err, ::std::chrono::nanoseconds *dp, F &&f)
Constructs a read operation with a completion task.
This header file is part of the I/O library; it contains the abstract CAN bus interface.
int io_can_ctrl_get_state(const io_can_ctrl_t *ctrl)
Returns the state of the CAN controller: one of CAN_STATE_ACTIVE, CAN_STATE_PASSIVE, CAN_STATE_BUSOFF, CAN_STATE_SLEEPING or CAN_STATE_STOPPED, or -1 on error.
void submit_write(const can_msg &msg, F &&f)
This header file is part of the I/O library; it contains the C++ CAN frame declarations.
bool abort_read(struct io_can_chan_read &read) noexcept
int io_can_ctrl_set_bitrate(io_can_ctrl_t *ctrl, int nominal, int data)
Configures the bitrate(s) of a CAN controller.
An abstract task executor. This class is a wrapper around ev_exec_t*.
CanState get_state() const
void submit_read(can_msg *msg, can_err *err, ::std::chrono::nanoseconds *dp, ev_exec_t *exec, F &&f)
bool read(can_msg *msg, can_err *err=nullptr, ::std::chrono::nanoseconds *dp=nullptr, int timeout=-1)
void io_can_chan_submit_write(io_can_chan_t *chan, struct io_can_chan_write *write)
Submits a write operation to a CAN channel.
This header file is part of the I/O library; it contains the C++ interface for the abstract I/O devic...
::std::error_code make_error_code(SdoErrc e) noexcept
Creates an error code corresponding to an SDO abort code.
typename ::std::enable_if< compat::is_invocable< F, int, ::std::error_code >::value, detail::CanChannelReadWrapper< F > * >::type make_can_channel_read_wrapper(can_msg *msg, can_err *err, ::std::chrono::nanoseconds *dp, ev_exec_t *exec, F &&f)
Creates a CAN channel read operation with a completion task.
This header file is part of the utilities library; it contains the time function declarations.
This header file is part of the I/O library; it contains the C++ CAN bus error definitions.
const struct io_can_ctrl_vtbl *const io_can_ctrl_t
An abstract CAN controller.
A reference to an abstract CAN controller.
ev::Future< void, int > async_write(const can_msg &msg, struct io_can_chan_write **pwrite=nullptr)
static size_t io_can_chan_abort_write(io_can_chan_t *chan, struct io_can_chan_write *write)
Aborts the specified CAN channel write operation if it is pending.
void write(const can_msg &msg, int timeout=-1)
int io_can_ctrl_restart(io_can_ctrl_t *ctrl)
(Re)starts a CAN contoller.
int io_can_ctrl_get_bitrate(const io_can_ctrl_t *ctrl, int *pnominal, int *pdata)
Obtains the bitrate(s) of a CAN controller.
const struct io_dev_vtbl *const io_dev_t
An abstract I/O device.
struct io_can_chan_write * io_can_chan_write_from_task(struct ev_task *task)
Obtains a pointer to a CAN channel write operation from a pointer to its completion task...
#define IO_CAN_CHAN_WRITE_INIT(msg, exec, func)
The static initializer for io_can_chan_write.
An abstract I/O device. This class is a wrapper around io_dev_t*.
int read(can_msg *msg, can_err *err, ::std::chrono::nanoseconds *dp, int timeout, ::std::error_code &ec) noexcept
int io_can_chan_get_flags(const io_can_chan_t *chan)
Returns the flafs of the CAN bus: any combination of IO_CAN_BUS_FLAG_ERR, IO_CAN_BUS_FLAG_FDF and IO_...
A reference to an abstract CAN channel.