diff --git a/nmrp.c b/nmrp.c index 1359e26..491088b 100644 --- a/nmrp.c +++ b/nmrp.c @@ -359,7 +359,7 @@ static void sigh(int sig) g_interrupted = 1; } -void nmrp_discard(struct ethsock *sock) +bool nmrp_discard(struct ethsock *sock) { // between nmrpflash sending the TFTP WRQ packet, and the router // responding with ACK(0)/OACK, some devices send extraneous @@ -377,7 +377,8 @@ void nmrp_discard(struct ethsock *sock) struct nmrp_pkt rx; - if (pkt_recv(sock, &rx) == 0) { + int ret = pkt_recv(sock, &rx); + if (ret == 0) { if (rx.msg.code != NMRP_C_CONF_REQ && rx.msg.code != NMRP_C_TFTP_UL_REQ) { printf("Discarding unexpected %s packet\n", msg_code_str(rx.msg.code)); } else if (verbosity > 1) { @@ -386,6 +387,7 @@ void nmrp_discard(struct ethsock *sock) } ethsock_set_timeout(sock, timeout); + return ret == 0; } static const char *spinner = "\\|/-"; diff --git a/nmrpd.h b/nmrpd.h index f3ae224..c64c14d 100644 --- a/nmrpd.h +++ b/nmrpd.h @@ -123,7 +123,7 @@ ssize_t tftp_put(struct nmrpd_args *args); bool tftp_is_valid_filename(const char *filename); int nmrp_do(struct nmrpd_args *args); -void nmrp_discard(struct ethsock *sock); +bool nmrp_discard(struct ethsock *sock); int select_fd(int fd, unsigned timeout); const char *mac_to_str(uint8_t *mac); diff --git a/tftp.c b/tftp.c index 40c67eb..ab6eb3e 100644 --- a/tftp.c +++ b/tftp.c @@ -328,7 +328,7 @@ ssize_t tftp_put(struct nmrpd_args *args) char rx[2048], tx[2048]; const char *file_remote = args->file_remote; char *val, *end; - bool rollover; + bool rollover, discard; const unsigned rx_timeout = MAX(args->rx_timeout / 50, 200); const unsigned max_timeouts = args->blind ? 3 : 5; #ifndef NMRPFLASH_WINDOWS @@ -414,6 +414,7 @@ ssize_t tftp_put(struct nmrpd_args *args) rollover = false; /* Not really, but this way the loop sends our WRQ before receiving */ timeouts = 1; + discard = true; pkt_mkwrq(tx, file_remote, TFTP_BLKSIZE); @@ -490,7 +491,9 @@ ssize_t tftp_put(struct nmrpd_args *args) } ret = tftp_recvfrom(sock, rx, &port, rx_timeout, blksize + 4); - nmrp_discard(args->sock); + if (discard) { + discard &= nmrp_discard(args->sock); + } if (ret < 0) { goto cleanup;