ASCII Serial Com
Serial communication library between computers, microcontrollers, FPGAs, etc. Uses only ASCII. Not the most efficient protocol, but meant to be easy to read
Loading...
Searching...
No Matches
circular_buffer_io_fd_poll.c
Go to the documentation of this file.
2
3#include <errno.h>
4#include <poll.h>
5#include <stdio.h>
6#include <unistd.h>
7
8/** \file */
9
10#define inflags(cb_io) cb_io->fds[0].revents
11#define outflags(cb_io) cb_io->fds[1].revents
12#define outsetflags(cb_io) cb_io->fds[1].events
13
16 circular_buffer_uint8 *out_buf, int fd_in,
17 int fd_out) {
18 cb_io->in_buf = in_buf;
19 cb_io->out_buf = out_buf;
20 cb_io->fd_in = fd_in;
21 cb_io->fd_out = fd_out;
22
23 cb_io->fds[0] = (struct pollfd){fd_in, POLLIN /*| POLLHUP*/, 0};
24 cb_io->fds[1] = (struct pollfd){fd_out, POLLHUP, 0};
25}
26
28 int timeout) {
29 if (!circular_buffer_is_empty_uint8(cb_io->out_buf)) {
30 outsetflags(cb_io) = POLLOUT | POLLHUP;
31 } else {
32 outsetflags(cb_io) = POLLHUP;
33 }
34 int ready = poll(cb_io->fds, 2, timeout);
35 if (ready < 0) {
36 perror("Error while polling");
37 fprintf(stderr, "Exiting.\n");
38 return 1;
39 }
40 if (circular_buffer_is_empty_uint8(cb_io->out_buf) &&
41 circular_buffer_is_empty_uint8(cb_io->in_buf)) {
42 if (inflags(cb_io) & POLLERR) {
43 fprintf(stderr, "Infile error, exiting.\n");
44 return 1;
45 }
46 if (inflags(cb_io) & POLLHUP) {
47 fprintf(stderr, "Infile hung up, exiting.\n");
48 return 1;
49 }
50 if (inflags(cb_io) & POLLNVAL) {
51 fprintf(stderr, "Infile closed, exiting.\n");
52 return 1;
53 }
54 }
55 if (outflags(cb_io) & POLLERR) {
56 fprintf(stderr, "Outfile error, exiting.\n");
57 return 1;
58 }
59 if (outflags(cb_io) & POLLHUP) {
60 fprintf(stderr, "Outfile hung up, exiting.\n");
61 return 1;
62 }
63 if (outflags(cb_io) & POLLNVAL) {
64 fprintf(stderr, "Outfile closed, exiting.\n");
65 return 1;
66 }
67
68 return 0;
69}
70
72 if (!(outflags(cb_io) & POLLOUT)) { // out fd not ready for writing
73 return 0;
74 }
75 return circular_buffer_pop_front_to_fd_uint8(cb_io->out_buf, cb_io->fd_out);
76}
77
79 if (!(inflags(cb_io) & POLLIN)) { // in fd not ready for reading
80 return 0;
81 }
82 return circular_buffer_push_back_from_fd_uint8(cb_io->in_buf, cb_io->fd_in);
83}
84
85void circular_buffer_io_fd_poll_print(circular_buffer_io_fd_poll *cb_io,
86 FILE *stream) {
87 fprintf(stream,
88 "circular_buffer_io_fd_poll: in buf: %p, out buf: %p, in fd: %i, out "
89 "fd: %i\n",
90 cb_io->in_buf, cb_io->out_buf, cb_io->fd_in, cb_io->fd_out);
91 fprintf(stream, "%12s%12s%12s\n", "", "events", "revents"); // 12 each
92 fprintf(stream, "%12s%12hi%12hi\n", "in POLLIN",
93 (short)(cb_io->fds[0].events & POLLIN),
94 (short)(cb_io->fds[0].revents & POLLIN));
95 fprintf(stream, "%12s%12hi%12hi\n", "in POLLPRI",
96 (short)(cb_io->fds[0].events & POLLPRI),
97 (short)(cb_io->fds[0].revents & POLLPRI));
98 fprintf(stream, "%12s%12hi%12hi\n", "in POLLOUT",
99 (short)(cb_io->fds[0].events & POLLOUT),
100 (short)(cb_io->fds[0].revents & POLLOUT));
101 fprintf(stream, "%12s%12hi%12hi\n", "in POLLHUP",
102 (short)(cb_io->fds[0].events & POLLHUP),
103 (short)(cb_io->fds[0].revents & POLLHUP));
104 fprintf(stream, "%12s%12hi%12hi\n", "out POLLIN",
105 (short)(cb_io->fds[1].events & POLLIN),
106 (short)(cb_io->fds[1].revents & POLLIN));
107 fprintf(stream, "%12s%12hi%12hi\n", "out POLLPRI",
108 (short)(cb_io->fds[1].events & POLLPRI),
109 (short)(cb_io->fds[1].revents & POLLPRI));
110 fprintf(stream, "%12s%12hi%12hi\n", "out POLLOUT",
111 (short)(cb_io->fds[1].events & POLLOUT),
112 (short)(cb_io->fds[1].revents & POLLOUT));
113 fprintf(stream, "%12s%12hi%12hi\n", "out POLLHUP",
114 (short)(cb_io->fds[1].events & POLLHUP),
115 (short)(cb_io->fds[1].revents & POLLHUP));
116 fprintf(stream, "%12s%12hi%12hi\n", "in raw", cb_io->fds[0].events,
117 cb_io->fds[0].revents);
118 fprintf(stream, "%12s%12hi%12hi\n", "out raw", cb_io->fds[1].events,
119 cb_io->fds[1].revents);
120}
size_t circular_buffer_pop_front_to_fd_uint8(circular_buffer_uint8 *circ_buf, const int fd)
circular buffer pop front writing to file descriptor
size_t circular_buffer_push_back_from_fd_uint8(circular_buffer_uint8 *circ_buf, int fd)
circular buffer push back reading from file descriptor
bool circular_buffer_is_empty_uint8(const circular_buffer_uint8 *circ_buf)
circular buffer get if empty
uint8_t circular_buffer_io_fd_poll_do_poll(circular_buffer_io_fd_poll *cb_io, int timeout)
poll circular buffer IO with file descriptor polling object
void circular_buffer_io_fd_poll_init(circular_buffer_io_fd_poll *cb_io, circular_buffer_uint8 *in_buf, circular_buffer_uint8 *out_buf, int fd_in, int fd_out)
Initialize circular buffer IO with file descriptor polling object.
size_t circular_buffer_io_fd_poll_do_input(circular_buffer_io_fd_poll *cb_io)
circular buffer IO with file descriptor polling object: read from input fd
size_t circular_buffer_io_fd_poll_do_output(circular_buffer_io_fd_poll *cb_io)
circular buffer IO with file descriptor polling object: write to output fd
Circular buffer IO with file descriptor polling.
Circular buffer IO with file descriptor polling struct.
circular buffer struct