diff --git a/include/patty/ax25/aprs_is.h b/include/patty/ax25/aprs_is.h index 2832db7..1e20ccf 100644 --- a/include/patty/ax25/aprs_is.h +++ b/include/patty/ax25/aprs_is.h @@ -37,6 +37,8 @@ int patty_ax25_aprs_is_fd(patty_ax25_aprs_is *aprs); int patty_ax25_aprs_is_ready(patty_ax25_aprs_is *aprs, fd_set *fds); +int patty_ax25_aprs_is_reset(patty_ax25_aprs_is *aprs); + ssize_t patty_ax25_aprs_is_fill(patty_ax25_aprs_is *aprs); ssize_t patty_ax25_aprs_is_drain(patty_ax25_aprs_is *aprs, diff --git a/include/patty/ax25/if.h b/include/patty/ax25/if.h index 876c86a..ee59952 100644 --- a/include/patty/ax25/if.h +++ b/include/patty/ax25/if.h @@ -41,6 +41,8 @@ typedef int (patty_ax25_if_driver_fd)(void *); typedef int (patty_ax25_if_driver_ready)(void *, fd_set *); +typedef int (patty_ax25_if_driver_reset)(void *); + typedef ssize_t (patty_ax25_if_driver_fill)(void *); typedef ssize_t (patty_ax25_if_driver_drain)(void *, void *, size_t); @@ -57,6 +59,7 @@ typedef struct _patty_ax25_if_driver { patty_ax25_if_driver_stats *stats; patty_ax25_if_driver_fd *fd; patty_ax25_if_driver_ready *ready; + patty_ax25_if_driver_reset *reset; patty_ax25_if_driver_fill *fill; patty_ax25_if_driver_drain *drain; patty_ax25_if_driver_pending *pending; @@ -123,6 +126,8 @@ int patty_ax25_if_fd(patty_ax25_if *iface); int patty_ax25_if_ready(patty_ax25_if *iface, fd_set *fds); +int patty_ax25_if_reset(patty_ax25_if *iface); + ssize_t patty_ax25_if_fill(patty_ax25_if *iface); ssize_t patty_ax25_if_drain(patty_ax25_if *iface, void *buf, size_t len); diff --git a/include/patty/kiss/tnc.h b/include/patty/kiss/tnc.h index 9a44450..a537190 100644 --- a/include/patty/kiss/tnc.h +++ b/include/patty/kiss/tnc.h @@ -37,6 +37,8 @@ int patty_kiss_tnc_fd(patty_kiss_tnc *tnc); int patty_kiss_tnc_ready(patty_kiss_tnc *tnc, fd_set *fds); +int patty_kiss_tnc_reset(patty_kiss_tnc *tnc); + void patty_kiss_tnc_destroy(patty_kiss_tnc *tnc); ssize_t patty_kiss_tnc_fill(patty_kiss_tnc *tnc); diff --git a/src/aprs_is.c b/src/aprs_is.c index c6e6895..96ca8c6 100644 --- a/src/aprs_is.c +++ b/src/aprs_is.c @@ -161,7 +161,7 @@ error_malloc_aprs: } void patty_ax25_aprs_is_destroy(patty_ax25_aprs_is *aprs) { - (void)close(aprs->fd); + close(aprs->fd); free(aprs); } @@ -178,19 +178,25 @@ int patty_ax25_aprs_is_ready(patty_ax25_aprs_is *aprs, fd_set *fds) { return FD_ISSET(aprs->fd, fds); } -ssize_t patty_ax25_aprs_is_fill(patty_ax25_aprs_is *aprs) { - int attempt = 0; +int patty_ax25_aprs_is_reset(patty_ax25_aprs_is *aprs) { + int attempt; - while ((aprs->readlen = read(aprs->fd, aprs->rx_buf, aprs->rx_bufsz)) < 0) { - if (errno == EIO) { - if (++attempt == PATTY_AX25_APRS_IS_ATTEMPTS_MAX) { - (void)aprs_is_connect(aprs, &aprs->info); - } - } else { - goto error_read; + close(aprs->fd); + + for (attempt=0; attemptinfo) == 0) { + return aprs->fd; } } + return -1; +} + +ssize_t patty_ax25_aprs_is_fill(patty_ax25_aprs_is *aprs) { + if ((aprs->readlen = read(aprs->fd, aprs->rx_buf, aprs->rx_bufsz)) < 0) { + goto error_read; + } + aprs->offset_i = 0; return aprs->readlen; @@ -450,6 +456,7 @@ patty_ax25_if_driver *patty_ax25_aprs_is_driver() { .stats = (patty_ax25_if_driver_stats *)patty_ax25_aprs_is_stats, .fd = (patty_ax25_if_driver_fd *)patty_ax25_aprs_is_fd, .ready = (patty_ax25_if_driver_ready *)patty_ax25_aprs_is_ready, + .reset = (patty_ax25_if_driver_reset *)patty_ax25_aprs_is_reset, .fill = (patty_ax25_if_driver_fill *)patty_ax25_aprs_is_fill, .drain = (patty_ax25_if_driver_drain *)patty_ax25_aprs_is_drain, .pending = (patty_ax25_if_driver_pending *)patty_ax25_aprs_is_pending, diff --git a/src/if.c b/src/if.c index 55d3bf1..6b839b9 100644 --- a/src/if.c +++ b/src/if.c @@ -286,6 +286,18 @@ int patty_ax25_if_ready(patty_ax25_if *iface, fd_set *fds) { iface->driver->ready(iface->phy, fds): 0; } +int patty_ax25_if_reset(patty_ax25_if *iface) { + int ret; + + if ((ret = iface->driver->reset(iface->phy)) < 0) { + iface->status = PATTY_AX25_IF_ERROR; + } else { + iface->status = PATTY_AX25_IF_UP; + } + + return ret; +} + ssize_t patty_ax25_if_fill(patty_ax25_if *iface) { return iface->driver->fill(iface->phy); } diff --git a/src/server.c b/src/server.c index 3fbd284..ebb9e73 100644 --- a/src/server.c +++ b/src/server.c @@ -2044,7 +2044,15 @@ static int handle_iface(patty_ax25_server *server, struct if_entry *entry) { } if ((len = patty_ax25_if_fill(entry->iface)) < 0) { - goto error_io; + int fd; + + fd_clear(server, entry->fd); + + if ((fd = patty_ax25_if_reset(entry->iface)) < 0) { + goto error_io; + } + + fd_watch(server, entry->fd = fd); } else if (len == 0) { close(entry->fd); diff --git a/src/tnc.c b/src/tnc.c index d11b58d..026dcc9 100644 --- a/src/tnc.c +++ b/src/tnc.c @@ -239,6 +239,12 @@ int patty_kiss_tnc_ready(patty_kiss_tnc *tnc, fd_set *fds) { return FD_ISSET(tnc->fd, fds); } +int patty_kiss_tnc_reset(patty_kiss_tnc *tnc) { + errno = ENOSYS; + + return -1; +} + static void tnc_drop(patty_kiss_tnc *tnc) { tnc->state = KISS_NONE; tnc->command = PATTY_KISS_RETURN; @@ -410,6 +416,7 @@ patty_ax25_if_driver *patty_kiss_tnc_driver() { .stats = (patty_ax25_if_driver_stats *)patty_kiss_tnc_stats, .fd = (patty_ax25_if_driver_fd *)patty_kiss_tnc_fd, .ready = (patty_ax25_if_driver_ready *)patty_kiss_tnc_ready, + .reset = (patty_ax25_if_driver_reset *)patty_kiss_tnc_reset, .fill = (patty_ax25_if_driver_fill *)patty_kiss_tnc_fill, .drain = (patty_ax25_if_driver_drain *)patty_kiss_tnc_drain, .pending = (patty_ax25_if_driver_pending *)patty_kiss_tnc_pending,