diff --git a/include/patty/ax25/sock.h b/include/patty/ax25/sock.h index 72e2bb4..a2c17ba 100644 --- a/include/patty/ax25/sock.h +++ b/include/patty/ax25/sock.h @@ -200,6 +200,8 @@ void patty_ax25_sock_vs_incr(patty_ax25_sock *sock); void patty_ax25_sock_vr_incr(patty_ax25_sock *sock); +int patty_ax25_sock_flow_full(patty_ax25_sock *sock); + /* * Frame segment reassembly state machine */ diff --git a/src/server.c b/src/server.c index 2b34c8c..a12aa19 100644 --- a/src/server.c +++ b/src/server.c @@ -1517,8 +1517,6 @@ static int handle_i(patty_ax25_server *server, } } - sock->va = frame->nr; - if (++sock->pending == sock->n_window_rx / 2) { sock->pending = 0; @@ -1597,7 +1595,6 @@ static int handle_rr(patty_ax25_server *server, patty_ax25_sock_send_rnr(sock, PATTY_AX25_FRAME_RESPONSE, 1); case PATTY_AX25_FRAME_RESPONSE: - sock->flow = PATTY_AX25_SOCK_READY; sock->va = frame->nr; sock->retries = sock->n_retry; @@ -1632,8 +1629,8 @@ static int handle_rnr(patty_ax25_server *server, patty_ax25_sock_send_rnr(sock, PATTY_AX25_FRAME_RESPONSE, 1); case PATTY_AX25_FRAME_RESPONSE: - sock->flow = PATTY_AX25_SOCK_WAIT; sock->va = frame->nr; + sock->flow = PATTY_AX25_SOCK_WAIT; sock->retries = sock->n_retry; fd_clear(server, sock->fd); @@ -1657,6 +1654,8 @@ static int handle_rej(patty_ax25_server *server, return 0; } + sock->va = frame->nr; + end = sock->vs; if (frame->nr > end) { @@ -1682,6 +1681,8 @@ static int handle_srej(patty_ax25_server *server, return 0; } + sock->va = frame->nr; + /* * TODO: Read the fine print of section 4.3.2.4 */ @@ -2111,7 +2112,9 @@ static int handle_sock(uint32_t key, /* * AX.25 v2.2, Section 6.4.1, "Sending I Frames" */ - if (sock->vs == sock->va + sock->n_window_tx) { + if (sock->flow == PATTY_AX25_SOCK_WAIT) { + sock->flow = PATTY_AX25_SOCK_READY; + } else if (patty_ax25_sock_flow_full(sock)) { sock->flow = PATTY_AX25_SOCK_WAIT; fd_clear(server, sock->fd); @@ -2119,7 +2122,7 @@ static int handle_sock(uint32_t key, patty_timer_stop(&sock->timer_t3); patty_timer_start(&sock->timer_t1, sock->n_ack); - return patty_ax25_sock_send_rr(sock, PATTY_AX25_FRAME_COMMAND, 1); + return 0; } if ((len = read(sock->fd, sock->rx_buf, sock->n_maxlen_rx)) < 0) { diff --git a/src/sock.c b/src/sock.c index bd4e3b3..9d6ef11 100644 --- a/src/sock.c +++ b/src/sock.c @@ -505,6 +505,14 @@ void *patty_ax25_sock_assembler_read(patty_ax25_sock *sock, return buf + 1; } +int patty_ax25_sock_flow_full(patty_ax25_sock *sock) { + if (sock->mode == PATTY_AX25_SOCK_SABME) { + return sock->vs == (sock->va + sock->n_window_tx) % 128? 1: 0; + } + + return sock->vs == (sock->va + sock->n_window_tx) % 8? 1: 0; +} + static inline int toobig(patty_ax25_sock *sock, size_t infolen) { return infolen > PATTY_AX25_FRAME_OVERHEAD + sock->n_maxlen_tx;